Welke operator (== vs ===) moet worden gebruikt in JavaScript-vergelijkingen?

Ik gebruik JSLintom JavaScript te doorlopen, en het geeft veel suggesties om ==(twee gelijktekens) met ===(drie isgelijk-tekens) bij het vergelijken van idSele_UNVEHtype.value.length == 0binnen van een if-statement.

Is er een prestatievoordeel bij het vervangen van ==door ===?

Elke prestatieverbetering zou welkom zijn aangezien er veel vergelijkingsoperators bestaan.

Als er geen typeconversie plaatsvindt, zou er dan een prestatiewinst zijn ten opzichte van ==?


Antwoord 1, autoriteit 100%

De operator voor strikte gelijkheid (===) gedraagt ​​zich identiek aan de operator voor abstracte gelijkheid (==), behalve dat er geen typeconversie wordt uitgevoerd en dat de typen de hetzelfde om als gelijk te worden beschouwd.

Referentie: Javascript-zelfstudie: vergelijkingsoperators

De operator ==vergelijkt voor gelijkheid na het uitvoeren van de nodige typeconversies. De operator ===zal nietde conversie uitvoeren, dus als twee waarden niet van hetzelfde type zijn, zal ===gewoon false. Beide zijn even snel.

Om Douglas Crockford’s uitstekende JavaScript: The Good Partste citeren,

JavaScript heeft twee sets gelijkheidsoperatoren: ===en !==, en hun kwaadaardige tweeling ==en !=. De goede werken zoals je zou verwachten. Als de twee operanden van hetzelfde type zijn en dezelfde waarde hebben, produceert ===trueen !==produceert false. De boze tweeling doet het juiste als de operanden van hetzelfde type zijn, maar als ze van verschillende typen zijn, proberen ze de waarden af ​​te dwingen. de regels waarmee ze dat doen zijn ingewikkeld en onmemorabel. Dit zijn enkele van de interessante gevallen:

'' == '0'           // false
0 == ''             // true
0 == '0'            // true
false == 'false'    // false
false == '0'        // true
false == undefined  // false
false == null       // false
null == undefined   // true
' \t\r\n ' == 0     // true

Gelijkheidsvergelijkingstabel

Het gebrek aan transitiviteit is alarmerend. Mijn advies is om nooit de boze tweeling te gebruiken. Gebruik in plaats daarvan altijd ===en !==. Alle zojuist getoonde vergelijkingen leveren falseop met de operator ===.


Bijwerken:

Een goed punt werd naar voren gebracht door @Casebashin de opmerkingen en in @Phillipe Laybaert’santwoordbetreffende objecten. Voor objecten gedragen ==en ===zich consistent met elkaar (behalve in een speciaal geval).

var a = [1,2,3];
var b = [1,2,3];
var c = { x: 1, y: 2 };
var d = { x: 1, y: 2 };
var e = "text";
var f = "te" + "xt";
a == b            // false
a === b           // false
c == d            // false
c === d           // false
e == f            // true
e === f           // true

Het speciale geval is wanneer je een primitief vergelijkt met een object dat evalueert naar dezelfde primitief, vanwege de toStringof valueOfmethode. Overweeg bijvoorbeeld de vergelijking van een string-primitief met een string-object dat is gemaakt met behulp van de String-constructor.

"abc" == new String("abc")    // true
"abc" === new String("abc")   // false

Hier controleert de operator ==de waarden van de twee objecten en retourneert true, maar de ===ziet dat ze zijn niet van hetzelfde type en retourneren false. Welke is juist? Dat hangt er echt van af wat je probeert te vergelijken. Mijn advies is om de vraag volledig te omzeilen en de String-constructor niet te gebruiken om tekenreeksobjecten te maken van letterlijke tekenreeksen.

Referentie
http://www.ecma-international.org/ecma- 262/5.1/#sec-11.9.3


Antwoord 2, autoriteit 18%

De operator ==gebruiken (Gelijkheid)

true == 1; //true, because 'true' is converted to 1 and then compared
"2" == 2;  //true, because "2" is converted to 2 and then compared

De operator ===gebruiken (Identiteit)

true === 1; //false
"2" === 2;  //false

Dit komt omdat de equality-operator ==wel dwang typt, wat inhoudt dat de interpreter impliciet probeert de waarden om te zetten voordat ze worden vergeleken.

Aan de andere kant, de identiteitsoperator ===voert geen dwang uit, en converteert dus de waarden niet bij het vergelijken, en is daarom sneller (zoals volgens Deze JS-benchmark-test) omdat deze één stap overslaat.


Antwoord 3, autoriteit 12%

Hier is een interessante visualisatie van de gelijkheidsvergelijking tussen ==en ===.

Bron: https://github.com/dorey/JavaScript-Equality-Table (demo, verenigde demo)


var1 === var2

Als je ===gebruikt voor het testen van JavaScript-gelijkheid, is alles zoals het is.
Niets wordt geconverteerd voordat het wordt geëvalueerd.

Gelijkheidsevaluatie van === in JS

var1 == var2

Als u ==gebruikt voor het testen van JavaScript-gelijkheid, vinden er enkele funky conversiesplaats.

Gelijkheidsevaluatie van == in JS

Samenvatting van gelijkheid in Javascript

Gelijkheid in Javascript


Conclusie:

Tenzij je de funky conversiesdie plaatsvinden met ==, gebruik altijd ===.


Antwoord 4, autoriteit 9%

In de antwoorden hier heb ik niets gelezen over wat gelijkbetekent. Sommigen zullen zeggen dat ===gelijk en van hetzelfde typebetekent, maar dat is niet echt waar. Het betekent eigenlijk dat beide operanden naar hetzelfde object verwijzen, of in het geval van waardetypes, dezelfde waarde hebben.

Dus laten we de volgende code nemen:

var a = [1,2,3];
var b = [1,2,3];
var c = a;
var ab_eq = (a === b); // false (even though a and b are the same type)
var ac_eq = (a === c); // true

Hetzelfde hier:

var a = { x: 1, y: 2 };
var b = { x: 1, y: 2 };
var c = a;
var ab_eq = (a === b); // false (even though a and b are the same type)
var ac_eq = (a === c); // true

Of zelfs:

var a = { };
var b = { };
var c = a;
var ab_eq = (a === b); // false (even though a and b are the same type)
var ac_eq = (a === c); // true

Dit gedrag is niet altijd duidelijk. Het verhaal is meer dan gelijk zijn en van hetzelfde type zijn.

De regel is:

Voor waardetypen (getallen):
a === bretourneert true als aen bdezelfde waarde hebben en van hetzelfde type zijn

Voor referentietypen:
a === bgeeft true terug als aen bnaar exact hetzelfde object verwijzen

Voor snaren:
a === bretourneert true als aen bbeide tekenreeksen zijn en exact dezelfde tekens bevatten


Strings: het speciale geval…

Strings zijn geen waardetypes, maar in Javascript gedragen ze zich als waardetypes, dus ze zullen “gelijk” zijn wanneer de karakters in de string hetzelfde zijn en wanneer ze dezelfde lengte hebben (zoals uitgelegd in de derde regel)

Nu wordt het interessant:

var a = "12" + "3";
var b = "123";
alert(a === b); // returns true, because strings behave like value types

Maar hoe zit het hiermee?:

var a = new String("123");
var b = "123";
alert(a === b); // returns false !! (but they are equal and of the same type)

Ik dacht dat strings zich gedragen als waardetypes? Nou, het hangt ervan af aan wie je het vraagt… In dit geval zijn a en b niet van hetzelfde type. ais van het type Object, terwijl bvan het type Stringis. Onthoud dat het maken van een string-object met behulp van de String-constructor iets van het type Objectcreëert dat zich meestalals een string gedraagt.


Antwoord 5, autoriteit 4%

Laat me deze raad toevoegen:

Lees bij twijfel de specificatie!

ECMA-262 is de specificatie voor een scripttaal waarvan JavaScript een dialect is. Natuurlijk is het in de praktijk belangrijker hoe de belangrijkste browsers zich gedragen dan een esoterische definitie van hoe iets zou moeten worden afgehandeld. Maar het is nuttig om te begrijpen waarom new String(“a”) !== “a”.

Laat me uitleggen hoe je de specificatie moet lezen om deze vraag te verduidelijken. Ik zie dat in dit zeer oude onderwerp niemand een antwoord had op het zeer vreemde effect. Dus als je een specificatie kunt lezen, zal dit je enorm helpen in je beroep. Het is een verworven vaardigheid. Dus laten we doorgaan.

Zoeken in het PDF-bestand naar === brengt me op pagina 56 van de specificatie: 11.9.4. The Strict Equals Operator ( === ), en na het doorwaden van de specificatie, vind ik:

11.9.6 Het strikte gelijkheidsvergelijkingsalgoritme
De vergelijking x === y, waarbij x en y waarden zijn, levert trueof falseop. Een dergelijke vergelijking wordt als volgt uitgevoerd:
  1. Als Type(x) anders is dan Type(y), retourneer dan false.
  2. Als Type(x) Undefined is, retourneert u true.
  3. Als Type(x) Null is, retourneert u true.
  4. Als Type(x) niet Getal is, ga dan naar stap 11.
  5. Als x NaNis, retourneert u false.
  6. Als y NaNis, retourneert u false.
  7. Als x dezelfde getalswaarde is als y, retourneert u true.
  8. Als x +0 is en y −0, retourneer dan true.
  9. Als x −0 is en y +0 is, retourneert u true.
  10. Retourneer false.
  11. Als Type(x) String is, retourneer dan trueals x en y exact dezelfde reeks tekens zijn (dezelfde lengte en dezelfde tekens op overeenkomstige posities); geef anders falseterug.
  12. Als Type(x) Booleaans is, retourneert u trueals x en y beide trueof beide falsezijn; geef anders falseterug.
  13. Retourneer trueals x en y verwijzen naar hetzelfde object of als ze verwijzen naar objecten die met elkaar zijn verbonden (zie 13.1.2). Geef anders falseterug.

Interessant is stap 11. Ja, strings worden behandeld als waardetypes. Maar dit verklaart niet waarom new String(“a”) !== “a”. Hebben we een browser die niet voldoet aan ECMA-262?

Niet zo snel!

Laten we eens kijken naar de typen operanden. Probeer het zelf uit door ze in typeof()te plaatsen. Ik vind dat new String(“a”)een object is, en stap 1 wordt gebruikt: retourneer falseals de typen verschillend zijn.

Als je je afvraagt ​​waarom new String(“a”)geen string retourneert, wat dacht je van een oefening om een ​​specificatie te lezen? Veel plezier!


Aidiakapi schreef dit in een reactie hieronder:

Van de specificatie

11.2.2 De nieuwe operator:

Als Type(constructor) geen Object is, gooi dan een TypeError-uitzondering.

Met andere woorden, als String niet van het type Object zou zijn, zou deze niet kunnen worden gebruikt met de nieuwe operator.

newretourneert altijd een Object, ook voor String-constructors. En helaas! De waardesemantiek voor strings (zie stap 11) gaat verloren.

En dit betekent uiteindelijk: new String(“a”) !== “a”.


Antwoord 6, autoriteit 2%

Ik heb dit in Firefox getest met Firebugmet de volgende code:

console.time("testEquality");
var n = 0;
while (true) {
  n++;
  if (n == 100000)
    break;
}
console.timeEnd("testEquality");

Snippet uitvouwen


Antwoord 7, autoriteit 2%

In PHP en JavaScript is het een strikte gelijkheidsoperator. Wat betekent dat het zowel het type als de waarden vergelijkt.


Antwoord 8

In JavaScript betekent dit van dezelfde waarde en hetzelfde type.

Bijvoorbeeld

4 == "4" // will return true

maar

4 === "4" // will return false 

Antwoord 9

Javascript-uitvoeringsstroomdiagram voor strikte gelijkheid / vergelijking ‘===’

Javascript strikte gelijkheid

Javascript-uitvoeringsstroomdiagram voor niet-strikte gelijkheid / vergelijking ‘==’

Javascript niet-gelijkheid


Antwoord 10

JavaScript ===vs==.

0==false   // true
0===false  // false, because they are of a different type
1=="1"     // true, auto type coercion
1==="1"    // false, because they are of a different type

Antwoord 11

Het betekent gelijkheid zonder typedwang
type dwang betekent dat JavaScript andere datatypes niet automatisch converteert naar string datatypes

0==false   // true,although they are different types
0===false  // false,as they are different types
2=='2'    //true,different types,one is string and another is integer but 
            javaScript convert 2 to string by using == operator 
2==='2'  //false because by using === operator ,javaScript do not convert 
           integer to string 
2===2   //true because both have same value and same types 

Antwoord 12

In een typisch script zal er geen prestatieverschil zijn. Belangrijker kan het feit zijn dat duizend “===” 1 KB zwaarder is dan duizend “==” 🙂 JavaScript-profilers kan u vertellen of er in uw geval een prestatieverschil is.

Maar persoonlijk zou ik doen wat JSLint voorstelt. Deze aanbeveling is er niet vanwege prestatieproblemen, maar omdat type dwang betekent dat ('\t\r\n' == 0)waar is.


Antwoord 13

De operator voor gelijke vergelijking == is verwarrend en moet worden vermeden.

Als je er MOETmee leven, onthoud dan de volgende 3 dingen:

  1. Het is niet transitief: (a == b)en (b == c)leidt niet tot (a == c )
  2. Het sluit elkaar uit voor zijn ontkenning: (a == b)en (a != b)hebben altijd tegengestelde Booleaanse waarden, met alle a en b.
  3. In geval van twijfel, leer de volgende waarheidstabel uit het hoofd:

GELIJKE OPERATOR WAARHEIDSTABEL IN JAVASCRIPT

  • Elke rij in de tabel is een set van 3 onderling “gelijke” waarden, wat betekent dat elke 2 waarden ertussen gelijk zijn met het gelijk == teken*

** STRANGE: merk op dat twee waarden in de eerste kolom in die zin niet gelijk zijn.**

''       == 0 == false   // Any two values among these 3 ones are equal with the == operator
'0'      == 0 == false   // Also a set of 3 equal values, note that only 0 and false are repeated
'\t'     == 0 == false   // -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
'\r'     == 0 == false   // -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
'\n'     == 0 == false   // -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
'\t\r\n' == 0 == false   // -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
null == undefined  // These two "default" values are not-equal to any of the listed values above
NaN                // NaN is not equal to any thing, even to itself.

14

Er is onwaarschijnlijk dat het een prestatieverschil tussen de twee operaties in uw gebruik is. Er is geen type-conversie die moet worden gedaan omdat beide parameters al hetzelfde type zijn. Beide bewerkingen hebben een type vergelijking gevolgd door een waardevergelijking.


15

===Operator controleert de waarden evenals de typen van de variabelen voor gelijkheid.

==operator controleert gewoon de waarde van de variabelen voor gelijkheid.


16

JSLINT geeft je soms onrealistische redenen om dingen aan te passen. ===heeft precies dezelfde prestaties als ==als de typen al hetzelfde zijn.

Het is alleen sneller wanneer de typen niet hetzelfde zijn, in welk geval het niet probeert typen te converteren, maar retourneert rechtstreeks een fout.

Dus, imho, jslint misschien gebruikt om nieuwe code te schrijven, maar nutteloos over-optimalisatie moet ten koste van alles worden vermeden.

Betekenis, er is geen reden om ==naar ===in een cheque zoals if (a == 'test')Als u het weet voor een feit dat A alleen een tekenreeks kan zijn.

Modificeren veel code op die manier verspilt de tijd van ontwikkelaars en reviewers en bereikt niets.


17

Als vuistregel, zou ik over het algemeen gebruik ===in plaats van ==(en !==in plaats van !=).

Reasons worden uitgelegd in de antwoorden boven en ook Douglas Crockford is vrij duidelijk over (JavaScript:. The Good Parts )

Er is echter een enkele uitzondering :
== nullis een efficiënte manier om te controleren op ‘is null of niet gedefinieerd’:

if( value == null ){
    // value is either null or undefined
}

Bijvoorbeeld jQuery 1.9.1 gebruikt dit patroon 43 keer en de JSHint-syntaxiscontrolebiedt om deze reden zelfs de ontspannende optie eqnull.

Uit de jQuery-stijlgids:

Strenge gelijkheidscontroles (===) moeten worden gebruikt in het voordeel van ==. De enige
uitzondering is bij het controleren op undefined en null door middel van null.

// Check for both undefined and null values, for some important reason. 
undefOrNull == null;

BEWERK 2021-03:

Tegenwoordig de meeste browsers
ondersteuning van de Nullish coalescing-operator (??)
en de Logische nullish-toewijzing (??=), wat een beknoptere manier mogelijk maakt om
wijs een standaardwaarde toe als een variabele null of ongedefinieerd is, bijvoorbeeld:

if (a.speed == null) {
  // Set default if null or undefined
  a.speed = 42;
}

kan als elk van deze vormen worden geschreven

a.speed ??= 42;
a.speed ?? a.speed = 42;
a.speed = a.speed ?? 42;

Antwoord 18

Een eenvoudig voorbeeld is

2 == '2'  -> true, values are SAME because of type conversion.
2 === '2'  -> false, values are NOT SAME because of no type conversion.

Antwoord 19

De top 2 antwoorden beide genoemde == betekent gelijkheid en === betekent identiteit. Helaas is deze stelling onjuist.

Als beide operanden van == objecten zijn, dan worden ze vergeleken om te zien of ze hetzelfde object zijn. Als beide operanden naar hetzelfde object wijzen, retourneert de gelijke-operator waar. Anders,
de twee zijn niet gelijk.

var a = [1, 2, 3];  
var b = [1, 2, 3];  
console.log(a == b)  // false  
console.log(a === b) // false  

In de bovenstaande code krijgen zowel == als === false omdat a en b niet dezelfde objecten zijn.

Dat wil zeggen: als beide operanden van == objecten zijn, gedraagt ​​== zich hetzelfde als ===, wat ook identiteit betekent. Het essentiële verschil tussen deze twee operators gaat over typeconversie. == heeft conversie voordat het de gelijkheid controleert, maar === niet.


Antwoord 20

Het probleem is dat u gemakkelijk in de problemen kunt komen, aangezien JavaScript veel impliciete conversies heeft, wat betekent…

var x = 0;
var isTrue = x == null;
var isFalse = x === null;

Wat al snel een probleem wordt. Het beste voorbeeld van waarom impliciete conversie “slecht” is, kan uit deze code worden gehaald in MFC/ C++ die daadwerkelijk zal compileren vanwege een impliciete conversie van CString naar HANDLE, wat een pointer typedef-type is…

CString x;
delete x;

Wat tijdens runtime duidelijk zeerongedefinieerde dingen doet…

Google voor impliciete conversies in C++ en STLom enkele van de argumenten ertegen te krijgen.. .


Antwoord 21

Van de core javascript-referentie

===Retourneert trueals de operanden strikt gelijk zijn (zie hierboven)
zonder typeconversie.


Antwoord 22

Gelijkheidsvergelijking:

Operator ==

Retourneert waar als beide operanden gelijk zijn. De operanden worden geconverteerd naar hetzelfde type voordat ze worden vergeleken.

>>> 1 == 1
true
>>> 1 == 2
false
>>> 1 == '1'
true

Gelijkheid en typevergelijking:

Operator ===

Retourneert waar als beide operanden gelijk en van hetzelfde type zijn. Het is over het algemeen
beter en veiliger als je op deze manier vergelijkt, omdat er geen typeconversies achter de schermen zijn.

>>> 1 === '1'
false
>>> 1 === 1
true

Antwoord 23

Hier is een handige vergelijkingstabel die de conversies laat zien die plaatsvinden en de verschillen tussen ==en ===.

Zoals de conclusie stelt:

‘Gebruik drie gelijken, tenzij u de conversies die nodig zijn volledig begrijpt
plaats voor twee gelijken.”

http://dorey.github.io/JavaScript-Equality-Table/


Antwoord 24

null en undefined zijn niets, dat wil zeggen,

var a;
var b = null;

Hier hebben aen bgeen waarden. Terwijl 0, false en ” allemaal waarden zijn. Een ding dat tussen al deze waarden gemeenschappelijk is, is dat het allemaal valse waarden zijn, wat betekent dat ze allemaal voldoenaan valse voorwaarden.

Dus de 0, false en ” vormen samen een subgroep. En aan de andere kant, null & undefined vormen de tweede subgroep. Controleer de vergelijkingen in de onderstaande afbeelding. null en undefined zouden gelijk zijn. De andere drie zouden aan elkaar gelijk zijn. Maar ze worden allemaal behandeld als valse voorwaarden in JavaScript.

Voer hier de afbeeldingsbeschrijving in

Dit is hetzelfde als elk object (zoals {}, arrays, enz.), niet-lege string & Boolean true zijn allemaal waarheidsgetrouwe voorwaarden. Maar ze zijn niet allemaal gelijk.

Other episodes