Equality in Lykn
JavaScript has four equality mechanisms. Lykn uses one.
The Four Mechanisms
Loose equality (==) coerces types before comparing. It is the source of most equality-related bugs and the mechanism that makes "" == false true. The coercion algorithm is seventeen steps long. Nobody has it memorized.
Strict equality (===) does not coerce. Different types are never equal. 5 === "5" is false. This is what you want virtually all the time.
Object.is is like === but handles two edge cases differently: NaN is equal to NaN (unlike ===), and +0 is not equal to -0 (unlike ===). Used when you need mathematically correct value identity.
SameValueZero is what Map, Set, and Array.prototype.includes use internally. Like Object.is but treats +0 and -0 as equal.
Lykn’s Choice
(= 5 "5") ;; → 5 === "5" → false
(= 5 5) ;; → 5 === 5 → true
(= null undefined) ;; → null === undefined → false
(= a b) compiles to a === b. Always. There is no surface form for loose equality. The entire coercion equality table — the one where transitivity goes to die — is simply inaccessible.
If you need loose equality (rare, but occasionally useful), the escape hatch is explicit:
(js:eq a b) ;; → a == b (explicit, greppable)
The == null Exception
There is one place where Lykn’s compiled output contains ==: the nil checks generated by some->, if-let, and when-let. The compiler emits x == null to catch both null and undefined in a single comparison — the only == check that ESLint’s eqeqeq rule explicitly exempts, and the only one that has a legitimate use case.
(some-> user (get :name) (:to-upper-case))
The compiled output includes == null checks at each step of the threading chain. You never write ==; the compiler uses it surgically, in a context where its behavior is well-defined and useful.
Why This Matters
BugAID’s pattern #4 — using == when === was needed — is one of the most prevalent bug patterns in the 105,133-commit dataset. CoffeeScript proved that compiling == to === unconditionally works, and the pattern was so successful that it influenced a generation of linting rules. Lykn follows the same principle: strict equality by default, loose equality only via explicit opt-in.