当代数在表达式之前时,代字号会做什么?

问题描述 投票:171回答:5
var attr = ~'input,textarea'.indexOf( target.tagName.toLowerCase() )
           ? 'value'
           : 'innerHTML'

我在答案中看到了它,我以前从未见过它。

这是什么意思?

javascript syntax bit-manipulation
5个回答
248
投票

~是一个bitwise operator,翻转其操作数中的所有位。

例如,如果您的数字是1,它的IEEE 754 float的二进制表示(JavaScript如何处理数字)将是......

0011 1111 1111 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000

所以~将其操作数转换为32位整数(JavaScript中的按位运算符)...

0000 0000 0000 0000 0000 0000 0000 0001

如果是负数,则将其存储在2的补码中:反转所有位并加1。

......然后翻转所有的东西......

1111 1111 1111 1111 1111 1111 1111 1110

那么它的用途是什么呢?什么时候可以使用它?

它有很多用途。如果你正在编写低级别的东西,它很方便。如果您对应用程序进行了分析并找到了瓶颈,那么可以通过使用按位技巧(在更大的包中作为一种可能的工具)来提高性能。

这也是一个(通常)不明确的技巧,将indexOf()发现的返回值转换为真实(虽然没有发现为虚假),人们经常使用它来将数字截断为32位的副作用(并通过将其加倍,有效地降低小数位)和Math.floor()一样为正数)。

我说不清楚,因为它的用途并不是很明显。通常,您希望您的代码能够清楚地与其他人阅读。虽然使用~可能看起来很酷,但它通常对自己的好处太聪明了。 :)

由于JavaScript有Array.prototype.includes()String.prototype.includes(),因此它的相关性也较低。这些返回一个布尔值。如果您的目标平台支持它,您应该更喜欢这个来测试字符串或数组中是否存在值。


98
投票

indexOf()表达式之前使用它有效地为您提供了一个真实/虚假的结果,而不是直接返回的数字索引。

如果返回值是-1,那么~-10,因为-1是一个全1位的字符串。任何大于或等于零的值都将给出非零结果。从而,

if (~someString.indexOf(something)) {
}

当“something”在“someString”中时,将导致if代码运行。如果你试图直接使用.indexOf()作为布尔值,那么这将不起作用,因为有时它返回零(当“某事物”在字符串的开头)。

当然,这也有效:

if (someString.indexOf(something) >= 0) {
}

而且它不那么神秘。

有时候你也会看到这个:

var i = ~~something;

像这样使用~运算符两次是将字符串转换为32位整数的快速方法。第一个~进行转换,第二个~翻转回来。当然,如果操作符应用于无法转换为数字的内容,则会得到NaN。 (编辑 - 实际上它是第一个应用的第二个~,但你明白了。)


23
投票

qazxsw poi是qazxsw poi,qazxsw poi与~大致相同。它更容易理解。所以:

Bitwise NOT Operator

考虑一下~x-(x+1)可以执行该操作以生产~2; // -(2+1) ==> -3

换句话说,与一系列数值一起使用的-(x+1)将仅对-1输入值产生一个假(从0强制到~)值,否则,任何其他真值。

众所周知,false通常被称为哨兵价值。它用于许多函数,它们返回0值以获得成功,而-1则返回C语言中的失败。在JavaScript中-1的返回值的规则相同。

通常以这种方式检查另一个字符串中子串的存在/不存在

>= 0

但是,如下所示通过-1更容易实现

indexOf()

var a = "Hello Baby"; if (a.indexOf("Ba") >= 0) { // found it } if (a.indexOf("Ba") != -1) { // found it } if (a.indexOf("aB") < 0) { // not found } if (a.indexOf( "aB" ) == -1) { // not found }


20
投票

~经常出现,这里的答案很棒,但也许有些人只需要知道如何使用它并“跳过”理论:

var a = "Hello Baby";

~a.indexOf("Ba");         // -7   -> truthy
if (~a.indexOf("Ba")) {   // true
    // found it
}

~a.indexOf("aB");         // 0    -> falsy
!~a.indexOf("aB");        // true
if (!~a.indexOf( "aB" )) {  // true
    // not found
}

11
投票

对于那些考虑使用波浪形技巧从You Don't Know JS: Types & Grammar by Kyle Simpson结果创建一个真值的人来说,它更明确,而且使用~indexOf(item)的魔法更少。

   if (~list.indexOf(item)) {
     // item in list
   } else {
     // item *not* in list
   }

请注意,这是ES 2015中的一种新标准方法,因此它不适用于旧版浏览器。如果重要,请考虑使用indexOf

此功能也可用于使用includes method on String的阵列:

'hello world'.includes('hello') //=> true
'hello world'.includes('kittens') //=> false

如果您需要较旧的浏览器支持,这是String.prototype.includes polyfill

© www.soinside.com 2019 - 2024. All rights reserved.