diff --git a/typescript/Hash Maps and Sets/geometric_sequence_triplets.ts b/typescript/Hash Maps and Sets/geometric_sequence_triplets.ts new file mode 100644 index 0000000..aa8ede8 --- /dev/null +++ b/typescript/Hash Maps and Sets/geometric_sequence_triplets.ts @@ -0,0 +1,20 @@ +function geometric_sequence_triplets(nums: number[], r: number): number { + const left_map: { [key: number]: number } = {}; + const right_map: { [key: number]: number } = {}; + let count = 0; + // Populate 'right_map' with the frequency of each element in the array. + for (const x of nums) + right_map[x] = (right_map[x] ?? 0) + 1; + // Search for geometric triplets that have x as the center. + for (const x of nums) { + // Decrement the frequency of x in right_map since x is now being + // processed and is no longer to the right. + right_map[x] -= 1; + if (x % r === 0) + count += (left_map[x / r] ?? 0) * (right_map[x * r] ?? 0); + // Increment the frequency of x in left_map since it'll be a part of the + // left side of the array once we iterate to the next value of x. + left_map[x] = (left_map[x] ?? 0) + 1; + } + return count; +} \ No newline at end of file diff --git a/typescript/Hash Maps and Sets/longest_chain_of_consecutive_numbers.ts b/typescript/Hash Maps and Sets/longest_chain_of_consecutive_numbers.ts new file mode 100644 index 0000000..e015097 --- /dev/null +++ b/typescript/Hash Maps and Sets/longest_chain_of_consecutive_numbers.ts @@ -0,0 +1,21 @@ +function longest_chain_of_consecutive_numbers(nums: number[]): number { + if (nums.length === 0) + return 0; + const num_set = new Set(nums); + let longest_chain = 0; + for (const num of num_set) { + // If the current number is the smallest number in its chain, search for + // the length of its chain. + if (!num_set.has(num - 1)) { + let currentNum = num; + let currentChain = 1; + // Continue to find the next consecutive numbers in the chain. + while (num_set.has(currentNum + 1)) { + currentNum += 1; + currentChain += 1; + } + longest_chain = Math.max(longest_chain, currentChain); + } + } + return longest_chain; +} \ No newline at end of file diff --git a/typescript/Hash Maps and Sets/longest_chain_of_consecutive_numbers_brute_force.ts b/typescript/Hash Maps and Sets/longest_chain_of_consecutive_numbers_brute_force.ts new file mode 100644 index 0000000..fbb8efe --- /dev/null +++ b/typescript/Hash Maps and Sets/longest_chain_of_consecutive_numbers_brute_force.ts @@ -0,0 +1,17 @@ +function longest_chain_of_consecutive_numbers_brute_force(nums: number[]): number { + if (nums.length === 0) + return 0; + let longest_chain = 0; + // Look for chains of consecutive numbers that start from each number. + for (const num of nums) { + let current_num = num; + let current_chain = 1; + // Continue to find the next consecutive numbers in the chain. + while (nums.includes(current_num + 1)) { + current_num += 1; + current_chain += 1; + } + longest_chain = Math.max(longest_chain, current_chain); + } + return longest_chain; +} \ No newline at end of file diff --git a/typescript/Hash Maps and Sets/pair_sum_unsorted.ts b/typescript/Hash Maps and Sets/pair_sum_unsorted.ts new file mode 100644 index 0000000..7fbbeb3 --- /dev/null +++ b/typescript/Hash Maps and Sets/pair_sum_unsorted.ts @@ -0,0 +1,9 @@ +function pair_sum_unsorted(nums: number[], target: number): number[] { + const hashmap = {} + for (let i = 0; i < nums.length; i++) { + if (hashmap[target - nums[i]] !== undefined) + return [hashmap[target - nums[i]], i] + hashmap[nums[i]] = i + } + return [] +} diff --git a/typescript/Hash Maps and Sets/pair_sum_unsorted_two_pass.ts b/typescript/Hash Maps and Sets/pair_sum_unsorted_two_pass.ts new file mode 100644 index 0000000..ec36b9d --- /dev/null +++ b/typescript/Hash Maps and Sets/pair_sum_unsorted_two_pass.ts @@ -0,0 +1,14 @@ +function pair_sum_unsorted_two_pass(nums: number[], target: number): number[] { + const num_map = {} + // First pass: Populate the hash map with each number and its + // index. + for (let i = 0; i < nums.length; i++) + num_map[nums[i]] = i + // Second pass: Check for each number's complement in the hash map. + for (let i = 0; i < nums.length; i++) { + const complement = target - nums[i] + if (num_map[complement] !== undefined && num_map[complement] !== i) + return [i, num_map[complement]] + } + return [] +} diff --git a/typescript/Hash Maps and Sets/verify_sudoku_board.ts b/typescript/Hash Maps and Sets/verify_sudoku_board.ts new file mode 100644 index 0000000..4f1dca7 --- /dev/null +++ b/typescript/Hash Maps and Sets/verify_sudoku_board.ts @@ -0,0 +1,29 @@ +function verify_sudoku_board(board: number[][]): boolean { + // Create hash sets for each row, column, and subgrid to keep + // track of numbers previously seen on any given row, column, or + // subgrid. + const row_sets: Set[] = Array.from({ length: 9 }, () => new Set()); + const column_sets: Set[] = Array.from({ length: 9 }, () => new Set()); + const subgrid_sets: Set[][] = Array.from({ length: 3 }, () => Array.from({ length: 3 }, () => new Set())); + for (let r = 0; r < 9; r++) { + for (let c = 0; c < 9; c++) { + const num = board[r][c]; + if (num === 0) + continue; + // Check if 'num' has been seen in the current row, + // column, or subgrid. + if (row_sets[r].has(num)) + return false; + if (column_sets[c].has(num)) + return false; + if (subgrid_sets[Math.floor(r / 3)][Math.floor(c / 3)].has(num)) + return false; + // If we passed the above checks, mark this value as seen + // by adding it to its corresponding hash sets. + row_sets[r].add(num); + column_sets[c].add(num); + subgrid_sets[Math.floor(r / 3)][Math.floor(c / 3)].add(num); + } + } + return true; +} \ No newline at end of file diff --git a/typescript/Hash Maps and Sets/zero_striping.ts b/typescript/Hash Maps and Sets/zero_striping.ts new file mode 100644 index 0000000..ac92317 --- /dev/null +++ b/typescript/Hash Maps and Sets/zero_striping.ts @@ -0,0 +1,55 @@ +function zero_striping(matrix: number[][]): void { + if (!matrix || !matrix[0]) + return; + const m = matrix.length, n = matrix[0].length; + // Check if the first row initially contains a zero. + let first_row_has_zero = false; + for (let c = 0; c < n; c++) { + if (matrix[0][c] === 0) { + first_row_has_zero = true; + break; + } + } + // Check if the first column initially contains a zero. + let first_col_has_zero = false; + for (let r = 0; r < m; r++) { + if (matrix[r][0] === 0) { + first_col_has_zero = true; + break; + } + } + // Use the first row and column as markers. If an element in the + // submatrix is zero, mark its corresponding row and column in the + // first row and column as 0. + for (let r = 1; r < m; r++) { + for (let c = 1; c < n; c++) { + if (matrix[r][c] === 0) { + matrix[0][c] = 0; + matrix[r][0] = 0; + } + } + } + // Update the submatrix using the markers in the first row and + // column. + for (let r = 1; r < m; r++) { + for (let c = 1; c < n; c++) { + if (matrix[0][c] === 0 || matrix[r][0] === 0) { + matrix[r][c] = 0; + } + } + } + // If the first row had a zero initially, set all elements in the + // first row to zero. + if (first_row_has_zero) { + for (let c = 0; c < n; c++) { + matrix[0][c] = 0; + } + } + // If the first column had a zero initially, set all elements in + // the first column to zero. + if (first_col_has_zero) { + for (let r = 0; r < m; r++) { + matrix[r][0] = 0; + } + } +} \ No newline at end of file diff --git a/typescript/Hash Maps and Sets/zero_striping_hash_sets.ts b/typescript/Hash Maps and Sets/zero_striping_hash_sets.ts new file mode 100644 index 0000000..dde4523 --- /dev/null +++ b/typescript/Hash Maps and Sets/zero_striping_hash_sets.ts @@ -0,0 +1,26 @@ +function zero_striping_hash_sets(matrix: number[][]): void { + if (!matrix || !matrix[0]) + return; + const m = matrix.length, n = matrix[0].length; + const zero_rows = new Set(), zero_cols = new Set(); + // Pass 1: Traverse through the matrix to identify the rows and + // columns containing zeros and store their indexes in the + // appropriate hash sets. + for (let r = 0; r < m; r++) { + for (let c = 0; c < n; c++) { + if (matrix[r][c] === 0) { + zero_rows.add(r); + zero_cols.add(c); + } + } + } + // Pass 2: Set any cell in the matrix to zero if its row index is + // in 'zero_rows' or its column index is in 'zero_cols'. + for (let r = 0; r < m; r++) { + for (let c = 0; c < n; c++) { + if (zero_rows.has(r) || zero_cols.has(c)) { + matrix[r][c] = 0; + } + } + } +} \ No newline at end of file