提问人:bcasp 提问时间:12/11/2008 最后编辑:Tarynbcasp 更新时间:5/7/2023 访问量:2118747
在 JavaScript 比较中应该使用哪个等于运算符 (== vs ===)?
Which equals operator (== vs ===) should be used in JavaScript comparisons?
问:
我正在使用 JSLint 来遍历 JavaScript,并且在执行诸如在语句内部进行比较之类的操作时,它返回了许多建议,将(两个等号)替换为(三个等号)。==
===
idSele_UNVEHtype.value.length == 0
if
替换为 是否有性能优势?==
===
任何性能改进都将受到欢迎,因为存在许多比较运算符。
如果没有发生类型转换,性能是否会提高?==
答:
严格相等运算符 () 的行为与抽象相等运算符 () 相同,只是没有进行类型转换,并且类型必须相同才能被视为相等。===
==
运算符将在执行任何必要的类型转换后比较是否相等。运算符不会进行转换,因此如果两个值不相同,则类型将仅返回 .两者都同样快。==
===
===
false
引用 Douglas Crockford 的优秀 JavaScript: The Good Parts,
JavaScript 有两组相等运算符:和 ,以及它们的邪恶双胞胎和 。好的按照你所期望的方式工作。如果两个操作数属于同一类型且具有相同的值,则 produce 和 produce .当操作数属于同一类型时,邪恶的双胞胎会做正确的事情,但如果它们属于不同的类型,他们就会试图胁迫这些值。他们这样做的规则是复杂且令人难忘的。以下是一些有趣的案例:
===
!==
==
!=
===
true
!==
false
'' == '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
缺乏传递性是令人担忧的。我的建议是永远不要使用邪恶的双胞胎。相反,请始终使用 和 .刚才显示的所有比较都与操作员一起产生。
===
!==
false
===
更新
@Casebash在评论和@Phillipe Laybaert 关于对象的回答中提出了一个很好的观点。对于对象,并且彼此一致(特殊情况除外)。==
===
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
特殊情况是,当您将基元与由于其 or 方法而计算为同一基元的对象进行比较时。例如,考虑将字符串基元与使用构造函数创建的字符串对象进行比较。toString
valueOf
String
"abc" == new String("abc") // true
"abc" === new String("abc") // false
在这里,运算符正在检查两个对象的值并返回 ,但看到它们不是同一类型并返回 。哪一个是正确的?这实际上取决于您要比较的内容。我的建议是完全绕过这个问题,不要使用构造函数从字符串文字创建字符串对象。==
true
===
false
String
参考
https://262.ecma-international.org/5.1/#sec-11.9.3
评论
-0
.toString()
定义为“0”
,但并非每种语言都这样做(例如,在 C# 中,是)。这可能会导致奇怪的修复,例如.Math.Round(-0.1).ToString()
"-0"
x == 0 ? 0 : x
(-0).toString()
(-0)
-0
使用运算符 (相等==
)
true == 1; //true, because 'true' is converted to 1 and then compared
"2" == 2; //true, because "2" is converted to 2 and then compared
使用运算符 (Identity===
)
true === 1; //false
"2" === 2; //false
这是因为相等运算符 ==
确实类型强制,这意味着解释器在比较之前隐式尝试转换值。
另一方面,恒等运算符 ===
不执行类型强制,因此在比较时不会转换值。
评论
===
Object.is
在您的使用中,这两个操作之间不太可能有任何性能差异。无需进行类型转换,因为两个参数已经是同一类型。这两个操作都将进行类型比较,然后进行值比较。
=== 运算符称为严格比较运算符,它与 == 运算符不同。
让我们取 2 个变量 a 和 b。
对于“a == b”,要计算为真,a 和 b 的值必须相同。
在“a === b”的情况下,a 和 b 必须是相同的值和类型,才能计算为 true。
以以下示例为例
var a = 1;
var b = "1";
if (a == b) //evaluates to true as a and b are both 1
{
alert("a == b");
}
if (a === b) //evaluates to false as a is not the same type as b
{
alert("a === b");
}
综上所述;在不希望使用 == 运算符的情况下,使用 == 运算符的计算结果可能会为 true,因此使用 === 运算符会更安全。
在 90% 的使用场景中,使用哪一个并不重要,但是当您有一天遇到一些意外行为时,了解差异会很方便。
在典型的脚本中,不会有性能差异。更重要的是,千个“===”比千个“==”重 1 KB:)JavaScript 探查器可以告诉您您的情况是否存在性能差异。
但就我个人而言,我会按照 JSLint 的建议去做。之所以提出此建议,不是因为性能问题,而是因为类型强制均值为真。('\t\r\n' == 0)
我使用如下代码在Firefox中使用Firebug对此进行了测试:
console.time("testEquality");
var n = 0;
while (true) {
n++;
if (n == 100000)
break;
}
console.timeEnd("testEquality");
和
console.time("testTypeEquality");
var n = 0;
while (true) {
n++;
if (n === 100000)
break;
}
console.timeEnd("testTypeEquality");
我的结果(每次测试五次并取平均值):
==: 115.2
===: 114.4
所以我想说微小的差异(记住,这是超过 100000 次迭代)可以忽略不计。性能不是这样做的理由。类型安全(嗯,就像你在 JavaScript 中获得的那样安全),代码质量是。===
评论
==
问题是你可能很容易遇到麻烦,因为 JavaScript 有很多隐式转换,这意味着......
var x = 0;
var isTrue = x == null;
var isFalse = x === null;
这很快就会成为一个问题。为什么隐式转换是“邪恶”的最佳示例可以从 MFC / C++ 中的这段代码中获取,由于从 CString 到 HANDLE 的隐式转换,它实际上将编译,这是一个指针类型定义类型......
CString x;
delete x;
显然,在运行时,它会做一些非常不确定的事情......
谷歌在 C++ 和 STL 中进行隐式转换,以获得一些反对它的论据......
评论
0 == null
是错误的。
在這裡的答案中,我沒有讀到任何關於平等意義的東西。有人会说这意味着平等和相同类型,但事实并非如此。这实际上意味着两个操作数引用同一个对象,或者在值类型的情况下,具有相同的值。===
因此,让我们采用以下代码:
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
同样在这里:
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
甚至:
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
这种行为并不总是显而易见的。这个故事不仅仅是平等和相同类型。
规则是:
对于值类型(数字):
如果 和 具有相同的值且属于同一类型,则返回 truea === b
a
b
对于引用类型:
如果引用完全相同的对象,则返回 truea === b
a
b
对于字符串:
如果 和 都是字符串并且包含完全相同的字符,则返回 truea === b
a
b
字符串:特例...
字符串不是值类型,但在 Javascript 中,它们的行为类似于值类型,因此当字符串中的字符相同且长度相同时,它们将是“相等的”(如第三条规则中所述)
现在它变得有趣:
var a = "12" + "3";
var b = "123";
alert(a === b); // returns true, because strings behave like value types
但是这个呢?
var a = new String("123");
var b = "123";
alert(a === b); // returns false !! (but they are equal and of the same type)
我以为字符串的行为像值类型?好吧,这取决于你问谁......在本例中,a 和 b 不是同一类型。 是类型,而 是类型。请记住,使用构造函数创建字符串对象会创建大多数时候表现为字符串的类型。a
Object
b
string
String
Object
让我补充一下这个忠告:
如有疑问,请阅读说明书!
ECMA-262 是以 JavaScript 为方言的脚本语言的规范。当然,在实践中,最重要的浏览器的行为方式比对如何处理某些东西的深奥定义更重要。但理解为什么 new String(“a”) !== “a” 是有帮助的。
请让我解释一下如何阅读规范来澄清这个问题。我看到在这个非常古老的话题中,没有人对这种非常奇怪的效果有答案。因此,如果您能阅读规范,这将对您的职业有很大帮助。这是一项后天习得的技能。所以,让我们继续。
在 PDF 文件中搜索 === 将我带到规范的第 56 页:11.9.4。严格等于运算符 ( === ),在浏览了规范后,我发现:
11.9.6 严格相等比较算法
比较 x === y,其中 x 和 y 是值,产生真或假。这种比较按如下方式进行:
1.如果 Type(x) 与 Type(y) 不同,则返回 false。
2. 如果 Type(x) 为 Undefined,则返回 true。
3. 如果 Type(x) 为 Null,则返回 true。
4. 如果 Type(x) 不是 Number,请转到步骤 11。
5. 如果 x 是 NaN,则返回 false。
6. 如果 y 为 NaN,则返回 false。
7. 如果 x 与 y 的数字值相同,则返回 true。
8. 如果 x 为 +0 且 y 为 −0,则返回 true。
9. 如果 x 为 −0 且 y 为 +0,则返回 true。
10. 返回 false。
11. 如果 Type(x) 为 String,则如果 x 和 y 是完全相同的字符序列(长度相同,对应位置的字符相同),则返回 true;否则,返回 false。
12. 如果 Type(x) 为布尔值,则如果 x 和 y 均为 true 或均为 false,则返回 true;否则,返回 false。
13. 如果 x 和 y 引用同一对象,或者它们引用相互连接的对象,则返回 true(参见 13.1.2)。否则,返回 false。
有趣的是第 11 步。是的,字符串被视为值类型。但这并不能解释为什么 new String(“a”) !== “a”。我们的浏览器是否不符合 ECMA-262?
没那么快!
让我们检查操作数的类型。通过将它们包装在 typeof() 中来自己尝试一下。我发现new String(“a”)是一个对象,并使用了步骤1:如果类型不同,则返回false。
如果你想知道为什么new String(“a”)不返回字符串,那么做一些阅读规范的练习怎么样?玩得愉快!
Aidiakapi 在下面的评论中写道:
从规格
11.2.2 新运算符:
如果 Type(constructor) 不是 Object,则引发 TypeError 异常。
换句话说,如果 String 不是 Object 类型,则它不能与 new 运算符一起使用。
new 始终返回一个 Object,即使对于 String 构造函数也是如此。唉!字符串的值语义(请参阅步骤 11)丢失。
这最终意味着:new String(“a”) !== “a”。
===
检查相同的边在类型和值上是否相等。
例:
'1' === 1 // will return "false" because `string` is not a `number`
常见示例:
0 == '' // will be "true", but it's very common to want this check to be "false"
另一个常见的例子:
null == undefined // returns "true", but in most cases a distinction is necessary
根据我的长期经验,最好使用非类型检查,因为您不在乎值是 、 还是undefined
null
0
""
另一种比较方法是使用,这里有一个很好的信息答案。Object.is
在 JavaScript 中,它表示相同的值和类型。
例如
4 == "4" // will return true
但
4 === "4" // will return false
在 PHP 和 JavaScript 中,它是一个严格的相等运算符。这意味着,它将比较类型和值。
这意味着没有类型强制的相等 类型强制意味着 JavaScript 不会自动将任何其他数据类型转换为字符串数据类型
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
===
如果操作数严格相等,则返回(见上文) 没有类型转换。true
===
运算符检查变量的值和类型是否相等。
==
运算符只是检查变量的值是否相等。
这是一项严格的检查测试。
这是一件好事,尤其是当您在 0 和 false 和 null 之间检查时。
例如,如果您有:
$a = 0;
然后:
$a==0;
$a==NULL;
$a==false;
所有返回 true,您可能不希望这样做。假设您有一个函数,该函数可以在失败时返回数组的第 0 个索引或 false。如果检查“==”false,则可能会得到令人困惑的结果。
所以与上面的东西相同,但要严格测试:
$a = 0;
$a===0; // returns true
$a===NULL; // returns false
$a===false; // returns false
评论
0 != null
等式比较运算符 == 令人困惑,应避免使用。
如果你必须忍受它,那么请记住以下 3 件事:
- 它不是传递的:(a == b) 和 (b == c) 不会导致 (a == c)
- 它与否定是互斥的:(a == b) 和 (a != b) 始终保持相反的布尔值,所有 a 和 b。
- 如有疑问,请牢记以下真相表:
JAVASCRIPT 中的相等运算符真值表
- 表中的每一行都是一组 3 个相互“相等”的值,这意味着其中任何 2 个值都使用等号 ==* 相等
** 奇怪:请注意,从这个意义上说,第一列上的任何两个值都不相等。
'' == 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.
JSLint 有时会给你一些不切实际的理由来修改东西。 具有完全相同的性能,就好像类型已经相同一样。===
==
只有当类型不同时,它才会更快,在这种情况下,它不会尝试转换类型,而是直接返回 false。
所以,恕我直言,JSLint 可能用于编写新代码,但应不惜一切代价避免无用的过度优化。
这意味着,没有理由在检查中更改为,就像你知道 a 只能是字符串这一事实一样。==
===
if (a == 'test')
以这种方式修改大量代码会浪费开发人员和审阅者的时间,并且一无所获。
评论
a.length===4
a.length==4
根据经验,我通常会使用 instead 而不是 (and instead of )。===
==
!==
!=
原因在上面的答案中得到了解释,道格拉斯·克罗克福德(Douglas Crockford)也非常清楚(JavaScript:好的部分)。
但是,有一个例外:是检查“为 null 或未定义”的有效方法:== null
if( value == null ){
// value is either null or undefined
}
例如,jQuery 1.9.1 使用了 43 次这种模式,JSHint 语法检查器甚至为此提供了宽松选项。eqnull
在jQuery风格指南中:
应使用严格的相等性检查 (===) 来支持 ==。唯一的 异常是通过 null 检查 undefined 和 null 时。
// Check for both undefined and null values, for some important reason.
undefOrNull == null;
编辑 2021-03:
如今,大多数浏览器都支持 Nullish 合并运算符 (??) 和逻辑 nullish 赋值
(??=)
,这允许更简洁的方式
如果变量为 null 或未定义,则分配默认值,例如:
if (a.speed == null) {
// Set default if null or undefined
a.speed = 42;
}
可以写成这些形式中的任何一种
a.speed ??= 42;
a.speed ?? a.speed = 42;
a.speed = a.speed ?? 42;
评论
JavaScript 与 .===
==
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
前 2 个答案都提到了 == 表示平等,=== 表示身份。不幸的是,这种说法是不正确的。
如果 == 的两个操作数都是对象,则对它们进行比较以查看它们是否是同一个对象。如果两个操作数都指向同一对象,则相等运算符返回 true。否则 两者并不相等。
var a = [1, 2, 3];
var b = [1, 2, 3];
console.log(a == b) // false
console.log(a === b) // false
在上面的代码中,== 和 === 都为 false,因为 a 和 b 不是同一个对象。
也就是说:如果 == 的两个操作数都是对象,则 == 的行为与 === 相同,这也意味着同一性。这两个运算符的本质区别在于类型转换。== 在检查相等性之前具有转换,但 === 没有。
相等性比较:
算子==
当两个操作数相等时,返回 true。在进行比较之前,操作数将转换为相同的类型。
>>> 1 == 1
true
>>> 1 == 2
false
>>> 1 == '1'
true
相等性和类型比较:
算子===
如果两个操作数相等且类型相同,则返回 true。一般来说 如果以这种方式进行比较,则更好更安全,因为没有幕后类型转换。
>>> 1 === '1'
false
>>> 1 === 1
true
*运算符 === vs == *
1 == true => true
true == true => true
1 === true => false
true === true => true
这是一个方便的比较表,显示了发生的转换以及 和 之间的差异。==
===
正如结论所述:
“除非您完全了解所需的转换,否则请使用三个等号 两个平等的地方。
http://dorey.github.io/JavaScript-Equality-Table/
null 和 undefined 是虚无的,即
var a;
var b = null;
这里没有值。而 0、false 和 '' 都是值。所有这些共同点是它们都是虚假值,这意味着它们都满足虚假条件。a
b
因此,0、false 和 '' 一起形成一个子组。另一方面,null 和 undefined 构成了第二个子组。检查下图中的比较。null 和 undefined 相等。其他三个将彼此相等。但是,它们在 JavaScript 中都被视为虚假条件。
这与任何对象(如{},数组等)相同,非空字符串和布尔值true都是真条件。但是,它们都不是平等的。
这是 和 之间的相等性比较的有趣可视化。==
===
来源:https://github.com/dorey/JavaScript-Equality-Table(demo,统一demo)
var1 === var2
当用于 JavaScript 相等性测试时,一切都是原样的。
在评估之前,不会转换任何内容。===
var1 == var2
当用于 JavaScript 相等性测试时,会发生一些时髦的转换。==
Javascript 中的平等总结
结论:
评论
==
NaN
)
==
a = []
b = false
c = [0]
JavaScript 既有严格的比较,也有类型转换的比较。严格比较(例如,)只有在操作数属于同一类型时才成立。更常用的抽象比较(例如)在进行比较之前将操作数转换为相同的类型。===
==
如果操作数不是同一类型,则 equality () 运算符会转换它们,然后应用严格的比较。如果操作数是数字或布尔值,则操作数将尽可能转换为数字;否则,如果任一操作数是字符串,则字符串操作数将尽可能转换为数字。如果两个操作数都是对象,则 JavaScript 会比较内部引用,当操作数引用内存中的同一对象时,这些引用是相等的。
==
语法:
x == y
例子:
3 == 3 // true "3" == 3 // true 3 == '3' // true
如果操作数严格相等(见上文),并且没有类型转换,则 identity/strict equality() 运算符返回 true。
===
语法:
x === y
例子:
3 === 3 // true
供参考:比较运算符(Mozilla Developer Network)
是的!这确实很重要。
===
JavaScript 中的运算符检查值和类型,而 AS 运算符只检查值(如果需要,进行类型转换)。==
您可以轻松测试它。将以下代码粘贴到 HTML 文件中,然后在浏览器中打开它
<script>
function onPageLoad()
{
var x = "5";
var y = 5;
alert(x === 5);
};
</script>
</head>
<body onload='onPageLoad();'>
您将在警报中得到“false”。现在修改方法,你会得到真。onPageLoad()
alert(x == 5);
如果您正在制作 Web 应用程序或安全页面,您应该始终使用(仅在可能的情况下)
===
因为它会检查它是否是相同的内容以及它是否是相同的类型!
因此,当有人输入时:
var check = 1;
if(check == '1') {
//someone continued with a string instead of number, most of the time useless for your webapp, most of the time entered by a user who does not now what he is doing (this will sometimes let your app crash), or even worse it is a hacker searching for weaknesses in your webapp!
}
但随着
var check = 1;
if(check === 1) {
//some continued with a number (no string) for your script
} else {
alert('please enter a real number');
}
黑客永远不会深入系统来发现错误并入侵您的应用程序或用户
我的观点是,
===
将为您的脚本增加更多安全性
当然,您也可以检查输入的数字是否有效,是否为字符串等。在第一个示例中使用其他 if 语句,但这至少对我来说更容易理解和使用
我发布这篇文章的原因是,在这次对话中从未说过“更安全”或“安全性”这个词(如果你看一下它使用 2019 次 === 和 1308 次 == iCloud.com,这也意味着你有时会使用 == 而不是 ===,否则它会阻止你的功能,但正如开头所说,你应该尽可能多地使用 ===)
只是
==
表示具有类型强制的操作数之间的比较
和
===
表示没有类型强制的操作数之间的比较。
JavaScript 中的类型强制意味着自动将数据类型转换为其他数据类型。
例如:
123 == "123" // Returns true, because JS coerces string "123" to number 123
// and then goes on to compare `123 == 123`.
123 === "123" // Returns false, because JS does not coerce values of different types here.
===
关心对象是否相同。因此,返回 false。但是,不关心对象是否相同;它只是简单地将一个参数转换为另一个参数的类型:如果无法转换,则返回 false。然后返回 true 而不是 false。new String("Hello world") === "Hello world"
==
new String("Hello world") == "Hello world"
评论
==
"undefined" != undefined
一个简单的例子是
2 == '2' -> true, values are SAME because of type conversion.
2 === '2' -> false, values are NOT SAME because of no type conversion.
javascript 是一种弱类型语言,即没有任何数据类型,如 C、c++ 等。int、boolean、float 等,因此变量可以保存任何类型的值,这就是为什么这些特殊的比较运算符存在的原因
例如
var i = 20;var j = "20";
如果我们应用比较运算符,这些变量的结果将是
i==j //result is true
或
j != i//result is false
为此,我们需要一个特殊的比较运算符来检查变量的值和数据类型
如果我们这样做
i===j //result is false
我的推理过程使用 emacs 组织模式和 node.js 来运行测试。
| use == | '' | '0' | false | 'false' | undefined | null | ' \t\r\n ' |
| '' | x | f | t | f | f | f | f |
| '0' | | x | t | f | f | f | f |
| false | | | x | f | f | f | t |
| 'false' | | | | x | f | f | f |
| undefined | | | | | x | t | f |
| null | | | | | | x | f |
| ' \t\r\n ' | | | | | | | x |
| use === | '' | '0' | false | 'false' | undefined | null | ' \t\r\n ' |
| '' | x | f | f | f | f | f | f |
| '0' | | x | f | f | f | f | f |
| false | | | x | f | f | f | f |
| 'false' | | | | x | f | f | f |
| undefined | | | | | x | f | f |
| null | | | | | | x | f |
| ' \t\r\n ' | | | | | | | x |
我的测试脚本如下:运行>节点xxx.js
var rowItems = ['', '0', false, 'false', undefined, null, ' \t\r\n ']
var colItems = rowItems
for(var i = 0; i < rowItems.length; i++) {
for (var j = 0; j < colItems.length; j++) {
var r = (rowItems[i] === colItems[j]) ? true : false;
console.log(rowItems[i] + " = " + colItems[j] + " " + r + " [" + i + "] ==> [" + j + "]")
};
}
严格相等的 Javascript 执行流程图 / 比较 '==='
非严格相等/比较 '==' 的 Javascript 执行流程图
是的,平等运算符和身份运算符之间有很大的区别。
通常,标识运算符的执行速度更快,因为没有进行类型转换。但是,如果值属于同一类型,则不会看到任何差异。
查看我的帖子 JavaScript 相等运算符的图例,其中解释了详细信息,包括类型转换和比较算法,并提供了大量示例。==
===
使用的一个未提及的原因是,如果您与 /交叉编译 to/from 共存。摘自 CoffeeScript 上的小书...===
coffee-script
JavaScript 中的弱相等比较有一些令人困惑的行为,通常是令人困惑的错误的根源。
解决方案是改用严格的相等运算符,它由三个等号组成:===。它的工作方式与普通相等运算符完全相同,但没有任何类型强制。建议始终使用严格的相等运算符,并在需要时显式转换类型。
如果您经常与 进行转换,则应仅使用 .事实上,编译器会强迫你...coffee-script
===
coffee-script
CoffeeScript 解决了这个问题,只需将所有弱比较替换为严格比较,换句话说,将所有 == 比较器转换为 ===。您不能在 CoffeeScript 中进行弱相等性比较,如有必要,您应该在比较类型之前显式转换类型。
始终使用“===”,您将避免数千个错误。如今,使用三重相等性更适合不同的风格指南,因为它比较考虑了操作数的类型。
Javascript 是松散类型的,就像 php 一样,
var x = "20";
var y =20;
if (x===y) // false
这总是会给你一个假,因为即使变量的值相同,数据类型也不是
一个是字符串,另一个是 int
If(x==y)//true
然而,这只会检查内容是否相同,而不管数据类型如何......
我不想说这些值相等,因为字符串值在逻辑上不能等于 int 值
var a = new String("123");
var b = "123";
alert(a === b); // returns false !! (but they are equal and of the same type)
在其中一个答案中看到了这一点。 并且在这种情况下不是真正的同一类型,如果您进行检查,您将获得“object”并且是“string”。a
b
typeof(a)
typeof(b)
为什么 ==
如此不可预测?
当你将空字符串与数字零进行比较时,你会得到什么?""
0
true
是的,没错,根据空字符串和数字零是同一时间。==
它并没有就此结束,这是另一个:
'0' == false // true
数组的事情变得非常奇怪。
[1] == true // true
[] == false // true
[[]] == false // true
[0] == false // true
然后用字符串更奇怪
[1,2,3] == '1,2,3' // true - REALLY?!
'\r\n\t' == 0 // true - Come on!
情况变得更糟:
什么时候等于不等于?
let A = '' // empty string
let B = 0 // zero
let C = '0' // zero string
A == B // true - ok...
B == C // true - so far so good...
A == C // **FALSE** - Plot twist!
让我再说一遍:
(A == B) && (B == C) // true
(A == C) // **FALSE**
而这只是你从基元中得到的疯狂的东西。
当您与对象一起使用时,这是一个全新的疯狂水平。==
在这一点上,你可能想知道......
为什么会这样?
嗯,这是因为与“三等”()不同,它只是检查两个值是否相同。===
==
做一大堆其他事情。
它对函数有特殊处理,对空值、未定义、字符串等进行特殊处理。
它变得非常古怪。
事实上,如果你尝试编写一个函数来执行该操作,它将看起来像这样:==
function isEqual(x, y) { // if `==` were a function
if(typeof y === typeof x) return y === x;
// treat null and undefined the same
var xIsNothing = (y === undefined) || (y === null);
var yIsNothing = (x === undefined) || (x === null);
if(xIsNothing || yIsNothing) return (xIsNothing && yIsNothing);
if(typeof y === "function" || typeof x === "function") {
// if either value is a string
// convert the function into a string and compare
if(typeof x === "string") {
return x === y.toString();
} else if(typeof y === "string") {
return x.toString() === y;
}
return false;
}
if(typeof x === "object") x = toPrimitive(x);
if(typeof y === "object") y = toPrimitive(y);
if(typeof y === typeof x) return y === x;
// convert x and y into numbers if they are not already use the "+" trick
if(typeof x !== "number") x = +x;
if(typeof y !== "number") y = +y;
// actually the real `==` is even more complicated than this, especially in ES6
return x === y;
}
function toPrimitive(obj) {
var value = obj.valueOf();
if(obj !== value) return value;
return obj.toString();
}
那么这意味着什么呢?
这意味着很复杂。==
因为它很复杂,所以很难知道使用它时会发生什么。
这意味着您最终可能会遇到错误。
所以这个故事的寓意是......
让你的生活不那么复杂。
使用代替 .===
==
结束。
首先,关于 Javascript 字符串等于的一些术语:Double equals 被正式称为抽象相等比较运算符,而 triple equals 被称为严格的相等比较运算符。它们之间的区别可以总结如下:抽象相等将尝试在进行比较之前通过类型强制来解析数据类型。如果类型不同,严格相等将返回 false。请看以下示例:
console.log(3 == "3"); // true
console.log(3 === "3"); // false.
console.log(3 == "3"); // true
console.log(3 === "3"); // false.
使用两个等号返回 true,因为在进行比较之前,字符串“3”已转换为数字 3。三个等号表示类型不同并返回 false。这是另一个:
console.log(true == '1'); // true
console.log(true === '1'); // false
console.log(true == '1'); // true
console.log(true === '1'); // false
同样,抽象相等性比较执行类型转换。在这种情况下,布尔值 true 和字符串 '1' 都转换为数字 1,结果为 true。严格相等返回 false。
如果你明白你正在区分 == 和 ===。但是,在某些情况下,这些运算符的行为并不直观。让我们再看一些例子:
console.log(undefined == null); // true
console.log(undefined === null); // false. Undefined and null are distinct types and are not interchangeable.
console.log(undefined == null); // true
console.log(undefined === null); // false. Undefined and null are distinct types and are not interchangeable.
console.log(true == 'true'); // false. A string will not be converted to a boolean and vice versa.
console.log(true === 'true'); // false
console.log(true == 'true'); // false. A string will not be converted to a boolean and vice versa.
console.log(true === 'true'); // false
下面的示例很有趣,因为它说明了字符串文本不同于字符串对象。
console.log("This is a string." == new String("This is a string.")); // true
console.log("This is a string." === new String("This is a string.")); // false
console.log("This is a string." == new String("This is a string.")); // true
console.log("This is a string." === new String("This is a string.")); // false
==
运算符只是比较值而不是数据类型。
===
运算符将值与其数据类型进行比较。
例如:
1 == "1" //true
1 === "1" //false
此运算符 () 用于执行自动类型转换的语言,例如。PHP,Javascript。
运算符有助于防止自动类型转换导致的意外比较。"==="
"==="
评论
如果你想在 JavaScript 中比较一些东西,请使用它,它被称为严格相等,这意味着如果只有类型和值都相同,这将返回 true,所以不会有任何不需要的类型更正,如果你使用 ,你基本上不关心类型,在许多情况下你可能会遇到松散相等性比较的问题。===
==
严格相等使用 ===
严格相等比较两个相等值。这两个值都不是 在进行比较之前隐式转换为其他值。如果 值具有不同的类型,这些值被认为是不相等的。 否则,如果值具有相同的类型并且不是数字, 如果它们具有相同的值,则它们被视为相等。最后,如果两者兼而有之 值是数字,如果它们都不是 NaN,则认为它们相等 并且是相同的值,或者如果一个是 +0 而一个是 -0。
var num = 0;
var obj = new String('0');
var str = '0';
console.log(num === num); // true
console.log(obj === obj); // true
console.log(str === str); // true
console.log(num === obj); // false
console.log(num === str); // false
console.log(obj === str); // false
console.log(null === undefined); // false
console.log(obj === null); // false
console.log(obj === undefined); // false
使用 == 的松散相等
松散相等在转换两个值后比较两个值是否相等 值设置为通用类型。转换后(一侧或两侧可能 进行转换),执行最终的相等性比较 完全按照 === 执行它。松散相等是对称的:A == B 对于 A 和 B 的任何值,始终与 B == A 具有相同的语义 (应用转换的顺序除外)。
var num = 0;
var obj = new String('0');
var str = '0';
console.log(num == num); // true
console.log(obj == obj); // true
console.log(str == str); // true
console.log(num == obj); // true
console.log(num == str); // true
console.log(obj == str); // true
console.log(null == undefined); // true
// both false, except in rare cases
console.log(obj == null);
console.log(obj == undefined);
评论
不同于 、 、
=
= =
= = =
=
operator 用于仅分配 .value
= =
operator 用于仅比较 notvalues
datatype
= = =
operator 用于比较 以及 。values
datatype
建议替换为的原因是运算符比 更可靠。在我们的上下文中,可靠的方法也适用于类型检查。考虑到最佳编程实践,我们应该始终选择更可靠的功能,而不是不太可靠的功能。同样,每当我们大多数时候考虑与运算符完全相等时,我们默认认为类型应该相同。提供相同的条件,我们应该去做。==
===
===
==
===
===
严格平等在大多数情况下更好
Javascript 是一种松散类型的语言,当你使用它时,它需要不断出现在你的脑海中。只要数据结构相同,就没有理由不使用严格的相等,对于常规相等,您通常会自动进行值的隐式转换,这会对您的代码产生深远的影响。这种转换很容易出现问题,因为它们会自动发生。
在严格相等的情况下,没有自动隐式转换,因为值必须已经具有正确的数据结构。
“我应该使用还是在 JavaScript 中进行比较”的困境等于或类似于以下问题:“我应该使用'勺子'还是'叉子'吃饭。==
===
这个问题唯一合理的答案是
- 您应该使用动态类型比较,例如:用于松散类型比较。
==
- 您应该使用静态类型比较,例如:用于强类型比较。
===
那是因为它们不一样。它们没有相同的目的,也不打算用于相同的目的。
当然,“叉子”和“勺子”都是用来“吃”的,但你会根据你吃的东西来选择使用它们。
意思是:你会下定决心使用“勺子”,即:用于“汤”,和/或“叉子”,即:用于采摘。==
===
问使用“叉子”还是“勺子”来“吃饭”更好 - 等于问在 JS 中使用静态 [===] 和动态 [==] 等式更好。这两个问题同样是错误的,反映了对有关主题的非常狭隘或肤浅的理解。
评论
length
dSele_UNVEHtype.value.length === 0
!dSele_UNVEHtype.value.length
评论