@orin00/deep-equal-util
v1.0.0
Published
A recursive deep equality comparison utility for Node.js and Browser environments.
Downloads
8
Maintainers
Readme
deep-equal-strict
A strict deep equality comparison utility for JavaScript.
Designed for correctness over performance, with explicit handling of edge cases such as NaN, -0, circular references, Map, Set, Symbol, and prototype checks.
This library intentionally avoids heuristic shortcuts and follows a well-defined comparison policy.
Features
- ✅ Strict numeric comparison
- Uses
Object.isonly NaNequalsNaN0and-0are treated as different
- Uses
- 🔁 Circular reference safe
- Uses symmetric pair caching with nested
WeakMap
- Uses symmetric pair caching with nested
- 🧠 Deep comparison
- Recursively compares:
- Objects
- Arrays
Map(including deep comparison of keys)Set(order-independent, 1:1 matching)
- Recursively compares:
- 🧬 Prototype-aware
- Objects with different prototypes are not equal
- 🧿 Symbol & non-enumerable properties
- Compared via
Reflect.ownKeys
- Compared via
- 🌐 UMD compatible
- Works in Node.js and browsers
Installation
npm
npm install deep-equal-strict
yarn
yarn add deep-equal-strict
Usage
CommonJS (Node.js)
""" const deepEqual = require('deep-equal-strict');
deepEqual({ a: 1 }, { a: 1 }); // true """
Browser (Global)
"""
"""
Examples
Basic Objects
""" deepEqual( { a: 1, b: { c: 2 } }, { a: 1, b: { c: 2 } } ); // true """
Strict Numeric Comparison
""" deepEqual(NaN, NaN); // true deepEqual(0, -0); // false """
Circular References
""" const a = {}; a.self = a;
const b = {}; b.self = b;
deepEqual(a, b); // true """
Map (Deep Key Comparison)
""" const mapA = new Map([[{ id: 1 }, 'value']]); const mapB = new Map([[{ id: 1 }, 'value']]);
deepEqual(mapA, mapB); // true """
Set (Order Independent)
""" const setA = new Set([{ x: 1 }, { y: 2 }]); const setB = new Set([{ y: 2 }, { x: 1 }]);
deepEqual(setA, setB); // true """
Symbols & Non-enumerable Properties
""" const sym = Symbol('key');
const a = {}; Object.defineProperty(a, sym, { value: 42 });
const b = {}; Object.defineProperty(b, sym, { value: 42 });
deepEqual(a, b); // true """
Prototype Mismatch
""" const a = { x: 1 }; const b = Object.create(null); b.x = 1;
deepEqual(a, b); // false """
Functions
""" const fn = () => 1;
deepEqual(fn, fn); // true deepEqual(() => 1, () => 1); // false """
Error Objects
""" deepEqual( new Error('fail'), new Error('fail') ); // usually false (stack differs) """
Design Notes (Strict Mode)
Correctness first, performance second
Map and Set comparisons are O(n²) by design
Functions are compared by reference only
Error objects are compared structurally and may differ by environment
Property descriptors (writable, getter, etc.) are not compared
This library is not intended to be a drop-in replacement for lodash.isEqual. It is designed for users who want predictable and explicit equality semantics.
When to Use
You need deterministic deep equality
You care about NaN, -0, and prototype correctness
You work with complex structures (Map, Set, circular graphs)
When NOT to Use
Performance-critical hot paths
JSON-only shallow comparisons
Heuristic or fuzzy equality needs
License : MIT
