Reports comparisons that are always true, always false, or can be simplified.
✅ This rule is included in the ts logical and logicalStrict presets.
This rule detects comparison patterns that are logically unnecessary, impossible, or can be simplified.
Such patterns often indicate logic errors, copy-paste mistakes, or overly complex code that should be refactored.
The rule covers several categories of problematic comparisons:
- Self-comparisons: Comparing a value to itself (e.g.,
x === x)
- Impossible ranges: Range checks that can never be satisfied (e.g.,
x <= 400 && x > 500)
- Redundant double comparisons: OR patterns that can be simplified (e.g.,
x === y || x < y can become x <= y)
- Ineffective checks: Redundant bounds in AND chains (e.g.,
x < 200 && x <= 299 where the second check is always true when the first is)
AE53 (valuAE=<==sp ansty="le--0:#D6DEEB;--1:#403F">53 value)==sp>< {d ivclassNa="meec-li">nt< sp ansty="le--0:#919F9F;--1:#5D63">76// Always tr sp> {d>5<3}d ivclassNa="meco"><}d>}d>3}d>AE53 (valuA53 value)< {d ivclassNa="meec-li">nt< sp ansty="le--0:#919F9F;--1:#5D63">76// Always fal sp> {d>5<3}d ivclassNa="meco"><}d>}d>3}d> 443F53 (va44A3F53 otherValude6376// Compare different va3<}di vdivclass="Nameexpressive-">6376// Use Number.isNaN() for NaN ch443F53 (Nu4<4AE. spans="tyle--0:#82AAFF;--1:#3B">61B0i4AE.>3F53(value<)) {divclass="Nameec-">de6376//)) >< .. .divclass="Nameec-">3 ..><..>}di>
76// Can never be true: no value is both <= 400 AND > 5<00d ivclassNa="meec-li">AE53 (AE<<=sp ansty="le--0:#D6DEEB;--1:#403F">5<=sp><3 sp ansty="le--0:#F78C6C;--1:#AA09">8243 sp><00sp ansty="le--0:#D6DEEB;--1:#403F">500sp><3 sp ansty="le--0:#C792EA;--1:#8844">AE3 sp><&&sp ansty="le--0:#D6DEEB;--1:#403F">53 &&sp>Asp ansty="le--0:#D6DEEB;--1:#403F">5sp><3 sp ansty="le--0:#F78C6C;--1:#AA09">8253 sp><00sp ansty="le--0:#D6DEEB;--1:#403F">53)00sp>00d>< {d ivclassNa="meec-li">nt< sp ansty="le--0:#919F9F;--1:#5D63">76// Unreachable co sp> {d>5<3}d ivclassNa="meco"> 500if (x <= 400 && x > 500) { // Unreachable code"><}d>}d>3}d>76// Impossible boundary conditiAE53 (A5<3 sp ansty="le--0:#F78C6C;--1:#AA09">83 sp><25sp ansty="le--0:#D6DEEB;--1:#403F">525sp><3 sp ansty="le--0:#C792EA;--1:#8844">AE3 sp><&&sp ansty="le--0:#D6DEEB;--1:#403F">53 &&sp>AE<>=sp ansty="le--0:#D6DEEB;--1:#403F">5>=sp><3 sp ansty="le--0:#F78C6C;--1:#AA09">83 sp><25sp ansty="le--0:#D6DEEB;--1:#403F">53)25sp>< {d ivclassNa="meec-li">nt< sp ansty="le--0:#919F9F;--1:#5D63">76// Never execut sp> {d>5<3}d ivclassNa="meco">= 5) { // Never executes"><}d>}d>3}d> 6376// Valid range: x is between 400 and< 50 0divclass="Nameec-">443F53< (x spans="tyle--0:#C792EA;--1:#88">44 (x >= spans="tyle--0:#D6DEEB;--1:#40">3=>098<2400 spans="tyle--0:#D6DEEB;--1:#40">32400>443F5<3 x spans="tyle--0:#C792EA;--1:#88">443 x >3098<2500 spans="tyle--0:#D6DEEB;--1:#40">3F52500> 50><3) {divclass="Nameec-">de6376//3) >< .. .divclass="Nameec-">3 ..>= 400 && x <= 500) { // ."><..><}di vdivclass="Nameexpressive-">6376// Valid narrow r443F53< (x spans="tyle--0:#C792EA;--1:#88">4 (x ><4AE> spans="tyle--0:#D6DEEB;--1:#40">34AE>>0<9825 spans="tyle--0:#D6DEEB;--1:#40">39825>443F5<3 x spans="tyle--0:#C792EA;--1:#88">43 x ><4AE< spans="tyle--0:#D6DEEB;--1:#40">34AE<>09<8210 spans="tyle--0:#D6DEEB;--1:#40">3F58210><3) {divclass="Nameec-">de6376//3) >< .. .divclass="Nameec-">3 ..> 5 && x < 10) { // ."><..>}di>
76// Can be simplified to: x <=< yd ivclassNa="meec-li">AE53 (AE=<==sp ansty="le--0:#D6DEEB;--1:#403F">53 ==sp>AE<||sp ansty="le--0:#D6DEEB;--1:#403F">53 ||sp>A53 y) yd>< {d ivclassNa="meec-li">nt< sp ansty="le--0:#919F9F;--1:#5D63">76// . sp> {d><..d ivclassNa="meec-li">5<3}d ivclassNa="meco"><}d>}d>3}d>76// Can be simplified to: x >=< yd ivclassNa="meec-li">AE53 (AE=<==sp ansty="le--0:#D6DEEB;--1:#403F">53 ==sp>AE<||sp ansty="le--0:#D6DEEB;--1:#403F">53 ||sp>Asp ansty="le--0:#D6DEEB;--1:#403F">53 y)sp> yd>< {d ivclassNa="meec-li">nt< sp ansty="le--0:#919F9F;--1:#5D63">76// . sp> {d><..d ivclassNa="meec-li">5<3}d ivclassNa="meco">= yif (x === y || x > y) { // ..."><}d>}d>3}d> 6376// Use the simpler combined oper443F53< (x spans="tyle--0:#C792EA;--1:#88">44 (x >3F53 de6376//< .. .divclass="Nameec-">3 ..><..><}di vdivclass="Nameexpressive-">443F53< (x spans="tyle--0:#C792EA;--1:#88">44 (x >= spans="tyle--0:#D6DEEB;--1:#40">3F53 =>de6376//< .. .divclass="Nameec-">3 ..>= y) { // ."><..>}di>
76// x <= 299 is redundant when x < 200 is already checkAE53 (A5<3 sp ansty="le--0:#F78C6C;--1:#AA09">8223 sp><00sp ansty="le--0:#D6DEEB;--1:#403F">500sp><3 sp ansty="le--0:#C792EA;--1:#8844">AE3 sp><&&sp ansty="le--0:#D6DEEB;--1:#403F">53 &&sp>AE<<=sp ansty="le--0:#D6DEEB;--1:#403F">5<=sp><3 sp ansty="le--0:#F78C6C;--1:#AA09">8223 sp><99sp ansty="le--0:#D6DEEB;--1:#403F">53)99sp>< {d ivclassNa="meec-li">nt< sp ansty="le--0:#919F9F;--1:#5D63">76// The second check adds nothi sp> {d>5<3}d ivclassNa="meco"><}d>}d>3}d>76// x >= 50 is redundant when x > 100 is already checkAE53 (Asp ansty="le--0:#D6DEEB;--1:#403F">5sp><3 sp ansty="le--0:#F78C6C;--1:#AA09">8213 sp><00sp ansty="le--0:#D6DEEB;--1:#403F">500sp><3 sp ansty="le--0:#C792EA;--1:#8844">AE3 sp><&&sp ansty="le--0:#D6DEEB;--1:#403F">53 &&sp>AE<>=sp ansty="le--0:#D6DEEB;--1:#403F">5>=sp><3 sp ansty="le--0:#F78C6C;--1:#AA09">823 sp><50sp ansty="le--0:#D6DEEB;--1:#403F">53)50sp>< {d ivclassNa="meec-li">nt< sp ansty="le--0:#919F9F;--1:#5D63">76// . sp> {d><..d ivclassNa="meec-li">5<3}d ivclassNa="meco">= 50 is redundant when x > 100 is already checkedif (x > 100 && x >= 50) { // ..."><}d>}d>3}d> 6376// Just use the stronger constr443F53< (x spans="tyle--0:#C792EA;--1:#88">4 (x ><4AE< spans="tyle--0:#D6DEEB;--1:#40">34AE<>098<2200 spans="tyle--0:#D6DEEB;--1:#40">3F52200><3) {divclass="Nameec-">de6376//3) >< .. .divclass="Nameec-">3 ..><..><}di vdivclass="Nameexpressive-">6376// Or use both bounds when they're actually ne443F53< (x spans="tyle--0:#C792EA;--1:#88">4 (x ><4AE> spans="tyle--0:#D6DEEB;--1:#40">34AE>>098<2100 spans="tyle--0:#D6DEEB;--1:#40">32100>443F5<3 x spans="tyle--0:#C792EA;--1:#88">43 x ><4AE< spans="tyle--0:#D6DEEB;--1:#40">34AE<>098<2200 spans="tyle--0:#D6DEEB;--1:#40">3F52200><3) {divclass="Nameec-">de6376// Valid range c3) >3 100 && x < 200) { // Valid range che">}di>
This rule is not configurable.
If your codebase relies on dynamic getters or other side effects that could make seemingly-identical expressions return different values, you might want to disable this rule for those specific cases.