Skip to content

Commit

Permalink
docs: Added example code for HashMap, Queue, and Stack.
Browse files Browse the repository at this point in the history
  • Loading branch information
zrwusa committed Dec 5, 2024
1 parent de0a2f1 commit 69f8e7d
Show file tree
Hide file tree
Showing 10 changed files with 613 additions and 6 deletions.
2 changes: 1 addition & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ All notable changes to this project will be documented in this file.
- [Semantic Versioning](https://semver.org/spec/v2.0.0.html)
- [`auto-changelog`](https://github.com/CookPete/auto-changelog)

## [v1.54.3](https://github.com/zrwusa/data-structure-typed/compare/v1.51.5...main) (upcoming)
## [v2.0.0](https://github.com/zrwusa/data-structure-typed/compare/v1.51.5...main) (upcoming)

### Changes

Expand Down
4 changes: 2 additions & 2 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

46 changes: 46 additions & 0 deletions src/data-structures/hash/hash-map.ts
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,52 @@ import { isWeakKey, rangeCheck } from '../../utils';
* 3. Unique Keys: Keys are unique.
* If you try to insert another entry with the same key, the new one will replace the old entry.
* 4. Unordered Collection: HashMap does not guarantee the order of entries, and the order may change over time.
* @example
* // should maintain insertion order
* const linkedHashMap = new LinkedHashMap<number, string>();
* linkedHashMap.set(1, 'A');
* linkedHashMap.set(2, 'B');
* linkedHashMap.set(3, 'C');
*
* const result = Array.from(linkedHashMap);
* console.log(result); // [
* // [1, 'A'],
* // [2, 'B'],
* // [3, 'C']
* // ]
* @example
* // fast lookup of values by key
* const hashMap = new HashMap<number, string>();
* hashMap.set(1, 'A');
* hashMap.set(2, 'B');
* hashMap.set(3, 'C');
*
* console.log(hashMap.get(1)); // 'A'
* console.log(hashMap.get(2)); // 'B'
* console.log(hashMap.get(3)); // 'C'
* console.log(hashMap.get(99)); // undefined
* @example
* // remove duplicates when adding multiple entries
* const hashMap = new HashMap<number, string>();
* hashMap.set(1, 'A');
* hashMap.set(2, 'B');
* hashMap.set(1, 'C'); // Update value for key 1
*
* console.log(hashMap.size); // 2
* console.log(hashMap.get(1)); // 'C'
* console.log(hashMap.get(2)); // 'B'
* @example
* // count occurrences of keys
* const data = [1, 2, 1, 3, 2, 1];
*
* const countMap = new HashMap<number, number>();
* for (const key of data) {
* countMap.set(key, (countMap.get(key) || 0) + 1);
* }
*
* console.log(countMap.get(1)); // 3
* console.log(countMap.get(2)); // 2
* console.log(countMap.get(3)); // 1
*/
export class HashMap<K = any, V = any, R = [K, V]> extends IterableEntryBase<K, V> {
/**
Expand Down
47 changes: 47 additions & 0 deletions src/data-structures/queue/queue.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,53 @@ import { LinearBase } from '../base/linear-base';
* 5. Data Buffering: Acting as a buffer for data packets in network communication.
* 6. Breadth-First Search (BFS): In traversal algorithms for graphs and trees, queues store elements that are to be visited.
* 7. Real-time Queuing: Like queuing systems in banks or supermarkets.
* @example
* // Sliding Window using Queue
* const nums = [2, 3, 4, 1, 5];
* const k = 2;
* const queue = new Queue<number>();
*
* let maxSum = 0;
* let currentSum = 0;
*
* nums.forEach((num, i) => {
* queue.push(num);
* currentSum += num;
*
* if (queue.length > k) {
* currentSum -= queue.shift()!;
* }
*
* if (queue.length === k) {
* maxSum = Math.max(maxSum, currentSum);
* }
* });
*
* console.log(maxSum); // 7
* @example
* // Breadth-First Search (BFS) using Queue
* const graph: { [key in number]: number[] } = {
* 1: [2, 3],
* 2: [4, 5],
* 3: [],
* 4: [],
* 5: []
* };
*
* const queue = new Queue<number>();
* const visited: number[] = [];
*
* queue.push(1);
*
* while (!queue.isEmpty()) {
* const node = queue.shift()!;
* if (!visited.includes(node)) {
* visited.push(node);
* graph[node].forEach(neighbor => queue.push(neighbor));
* }
* }
*
* console.log(visited); // [1, 2, 3, 4, 5]
*/
export class Queue<E = any, R = any> extends LinearBase<E, R> {
constructor(elements: Iterable<E> | Iterable<R> = [], options?: QueueOptions<E, R>) {
Expand Down
2 changes: 1 addition & 1 deletion test/unit/data-structures/binary-tree/avl-tree.test.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { AVLTree, AVLTreeNode, BinaryTreeNode, BSTNode, Range } from '../../../../src';
import { AVLTree, AVLTreeNode, BinaryTreeNode, BSTNode } from '../../../../src';

describe('AVL Tree Test', () => {
it('should perform various operations on a AVL Tree', () => {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { BinaryTreeNode, BSTNode, Range, RedBlackTree, RedBlackTreeNode } from '../../../../src';
import { BinaryTreeNode, BSTNode, RedBlackTree, RedBlackTreeNode } from '../../../../src';
import { getRandomInt, getRandomIntArray, magnitude } from '../../../utils';
import { OrderedMap } from 'js-sdsl';

Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { BinaryTreeNode, BSTNode, Range, TreeMultiMap, TreeMultiMapNode } from '../../../../src';
import { BinaryTreeNode, BSTNode, TreeMultiMap, TreeMultiMapNode } from '../../../../src';
import { getRandomInt } from '../../../utils';

import { isDebugTest } from '../../../config';
Expand Down
135 changes: 135 additions & 0 deletions test/unit/data-structures/hash/hash-map.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -842,3 +842,138 @@ describe('LinkedHashMap', () => {
});
});
});

describe('classic uses', () => {
it('@example should maintain insertion order', () => {
const linkedHashMap = new LinkedHashMap<number, string>();
linkedHashMap.set(1, 'A');
linkedHashMap.set(2, 'B');
linkedHashMap.set(3, 'C');

const result = Array.from(linkedHashMap);
expect(result).toEqual([
[1, 'A'],
[2, 'B'],
[3, 'C']
]);
});

it('should allow reverse iteration', () => {
const linkedHashMap = new LinkedHashMap<number, string>();
linkedHashMap.set(1, 'A');
linkedHashMap.set(2, 'B');
linkedHashMap.set(3, 'C');

const result = Array.from(linkedHashMap.reverseBegin());
expect(result).toEqual([
[3, 'C'],
[2, 'B'],
[1, 'A']
]);
});

it('should allow fast deletion at an index', () => {
const linkedHashMap = new LinkedHashMap<number, string>();
linkedHashMap.set(1, 'A');
linkedHashMap.set(2, 'B');
linkedHashMap.set(3, 'C');

linkedHashMap.deleteAt(1);

const result = Array.from(linkedHashMap);
expect(result).toEqual([
[1, 'A'],
[3, 'C']
]);
});

it('should filter entries correctly', () => {
const linkedHashMap = new LinkedHashMap<number, string>();
linkedHashMap.set(1, 'A');
linkedHashMap.set(2, 'B');
linkedHashMap.set(3, 'C');

const filteredMap = linkedHashMap.filter((key, value) => value !== 'B');

const result = Array.from(filteredMap);
expect(result).toEqual([
[1, 'A'],
[3, 'C']
]);
});

it('should map entries to a new LinkedHashMap', () => {
const linkedHashMap = new LinkedHashMap<number, string>();
linkedHashMap.set(1, 'A');
linkedHashMap.set(2, 'B');

const mappedMap = linkedHashMap.map((key, value) => [value, key]);

const result = Array.from(mappedMap);
expect(result).toEqual([
['A', 1],
['B', 2]
]);
});
});

describe('classic uses', () => {
it('@example fast lookup of values by key', () => {
const hashMap = new HashMap<number, string>();
hashMap.set(1, 'A');
hashMap.set(2, 'B');
hashMap.set(3, 'C');

expect(hashMap.get(1)).toBe('A');
expect(hashMap.get(2)).toBe('B');
expect(hashMap.get(3)).toBe('C');
expect(hashMap.get(99)).toBeUndefined(); // Key not present
});

it('@example remove duplicates when adding multiple entries', () => {
const hashMap = new HashMap<number, string>();
hashMap.set(1, 'A');
hashMap.set(2, 'B');
hashMap.set(1, 'C'); // Update value for key 1

expect(hashMap.size).toBe(2);
expect(hashMap.get(1)).toBe('C');
expect(hashMap.get(2)).toBe('B');
});

it('@example count occurrences of keys', () => {
const data = [1, 2, 1, 3, 2, 1];

const countMap = new HashMap<number, number>();
for (const key of data) {
countMap.set(key, (countMap.get(key) || 0) + 1);
}

expect(countMap.get(1)).toBe(3);
expect(countMap.get(2)).toBe(2);
expect(countMap.get(3)).toBe(1);
});

it('should group entries by a key-derived property', () => {
const entries = [
{ id: 1, group: 'A' },
{ id: 2, group: 'B' },
{ id: 3, group: 'A' },
{ id: 4, group: 'B' }
];

const groupedMap = new HashMap<string, number[]>();

for (const entry of entries) {
const group = entry.group;
const id = entry.id;
if (!groupedMap.has(group)) {
groupedMap.set(group, []);
}
groupedMap.get(group)?.push(id);
}

expect(groupedMap.get('A')).toEqual([1, 3]);
expect(groupedMap.get('B')).toEqual([2, 4]);
});
});
Loading

0 comments on commit 69f8e7d

Please sign in to comment.