37 lines
925 B
TypeScript
37 lines
925 B
TypeScript
type Value = string | number | boolean | null | undefined | Value[] | { [key: string]: Value };
|
|
|
|
export function arrayDedup<T extends Value>(arr: T[]): T[] {
|
|
const seen = new Map<string, T>();
|
|
|
|
for (const item of arr) {
|
|
const key = stableStringify(item);
|
|
if (!seen.has(key)) {
|
|
seen.set(key, item);
|
|
}
|
|
}
|
|
|
|
return Array.from(seen.values());
|
|
}
|
|
|
|
/**
|
|
* Deterministic stringify:
|
|
* - sorts object keys
|
|
* - preserves arrays order
|
|
* - distinguishes undefined/null
|
|
*/
|
|
function stableStringify(value: Value): string {
|
|
if (value === undefined) return 'undefined';
|
|
if (value === null) return 'null';
|
|
|
|
if (Array.isArray(value)) {
|
|
return `[${value.map(stableStringify).join(',')}]`;
|
|
}
|
|
|
|
if (typeof value === 'object') {
|
|
const keys = Object.keys(value).sort();
|
|
return `{${keys.map((k) => `${k}:${stableStringify(value[k])}`).join(',')}}`;
|
|
}
|
|
|
|
return `${typeof value}:${String(value)}`;
|
|
}
|