![](https://i-blog.csdnimg.cn/blog_migrate/6198895c86ef499b98a9d19e3984ec1a.png)
在本系列文章中,我们从JavaScript的角度介绍了不同的计算机科学主题。 我们已经尝试了不同的算法,并对一堆数组进行了排序。 但是,回到最基本的概念总是一个好主意。
当我说基本时,我指的是所有这些中最基本的东西,即一和零,也称为位。 公平地讲,我一直忽略按位运算,因为我不在日常工作中使用它们,并且可能永远也不会使用它们。 但是对于计算机而言,一切都取决于他们。
了解位和按位操作不会使您成为更好的JavaScript开发人员。 它可能对您正在使用的React应用程序没有帮助,但通常可以使您成为更好的软件开发人员。
您不需要一无所知,实际上您将永远不会记住这一切。 我在本文中的目标将是涵盖关于位和位操作必须具备的最基本的知识。
什么是位?
好的,因此从技术上讲,对于计算机而言,一切都降至1和0。 它不能与数字,字符或字符串一起使用,它仅使用二进制数字(位)。 这种解释的简短形式是所有内容都以二进制形式存储。 然后,计算机使用UTF-8等编码将保存的位组合映射到字符,数字或其他符号(ELI5版本)。
您拥有的位数越多,排列和表示的内容就越多。
让我们以数字113为例。 JS中获取二进制格式最简单的方法是这样的: Number(113).toString(2)
。 这将给我们1110001
。 知道一切都只是底层,我们现在来看一下如何操作它们。
很多文章都带有十六进制数字的示例。 在这一本书中,我们将只看十进制数和二进制数。 其背后的原因是我发现这更加直观。 如有疑问,您基本上可以在纸上写下这些位和所有操作,并跟踪正在发生的事情。
还有一点需要注意的是,无法直接在JavaScript中输入二进制文件。 如果要将二进制数转换为十进制数,可以使用parseInt
函数: parseInt(1111, 2) // 15
。
&(与)
就像我们在日常编程任务中一直在使用的&&
逻辑运算符一样,如果两个比较位均为1,则返回1。 它在两端都使用一个数字(数字,不是二进制形式),然后将它们的位一一比较。
让我们想象一下。 数字12
和15
具有1100
和1111
的二进制表示形式。 让我们在这些数字上使用&
运算符。 如果您仅注销,则将再次收到12
。 很奇怪,那有什么作用吗?
是的,它将12
每个位与15
的对应位进行了比较,并且由于操作员如何工作,它又得到了1100
,实际上是12
。
&
运算符的一个有趣技巧是找出数字是偶数还是奇数。 如果数字为奇数,则其第一位始终为1
。 因此,我们可以使用&
并将数字与1
进行比较,因此,如果数字为奇数,则结果将为1
。 但是,我不建议您在实际的代码库中使用它,因为这样做不清楚。
| (要么)
这个工作原理很像||
一。 它用于通过每次比较返回1
来逐位比较两个二进制数,其中当比较的位都为0
时,至少有一个1
和0
。 如果我们采用前面的示例并使用此运算符12 | 15
12 | 15
将返回15
。 为什么这样?
1100 | 1111
1100 | 1111
将为每个比较返回1
,它再次等于1111
或15
。
〜(不)
这是位非。 结果为二进制补码算术中的e负数。 它的作用是将所有位从1还原为0,反之亦然。
不过,如果你登出~15
,你会看到的结果是-16
,即使位是正确的。 这是因为在二进制补码算法中,为了获得数字的负表示,您首先需要翻转它的位,然后对其加1。
您可以在Google上搜索以获得更好的解释,但这只是您想当然的事情之一。
^(异或)
此运算符称为XOR运算符或异或。 像&
和|
运算符会计算双方的数字,从而进行比较。
它会比较的对应位并返回1
,只有一个单一的,只有当1
。 也许这不是一个很好的解释,所以让我们给出一个更直观的解释。 1 ^ 0
将返回1
。 但是1 ^ 1
将返回0
。
^
运算符仅在将1
与0
进行比较的特定情况下才返回1。
移位运算符
有两个处理移位位的运算符- >>
和<<
。 您可能会猜到它们之间的区别是它们将数字的位数移位的位置。
<<
运算符将数字的所有位移位n
次。 这里要注意的是,数字移位时出现的空白全部用0填充。
另一方面, >>
运算符向右移动。 此运算符与前一个移位运算符的区别在于,该运算符将用0填充正数位,并用1填充负数位。
这里是要指出的地方,通常数字的第一位用来表示它的符号。 如果为1
,则为负;如果为0
,则为正。 因此,正确移动背后的原因是为了保持我们正在移动的数字的符号。
位操作
现在我们知道了运算符的作用,下面让我们看一下如何利用它们来操作位。
假设我们要在给定位置设置一点。 我们希望从右边开始设置第二个位(为1
)。 这使我们想到了口罩的概念。 掩码是二进制形式的数字,根据要实现的目标,我们仅将要修改的位设置为1
或0
。 我们也可以说它们被用作标志来定义要更改的位。
如果要设置第一位,则掩码将为0001
。 万一我们想设置第二个为0010
,依此类推。
一个示例将使这一点更加清楚:
到目前为止,一切都很好。 让我们看一下如何清除它-将其设置为0
。 这不会像前面的示例那样容易,因为我们需要保持所有其他位不变。
此处的区别在于,我们要使掩码全为1,而仅在要清除的位置为0
。 然后,我们使用&
运算符将仅将所需位置设置为0
。
现在我们知道如何设置和清除位,但是如果我们想翻转它怎么办? 我们不知道该位是否设置,但我们确实希望更改其当前状态。 这是XOR的工作。
在这种情况下使用XOR,是因为将XOR与1
一起使用可以保证翻转该位的值。
结论
这篇文章的目的是介绍位操作和运算符的基础知识。 即使我们只是勉强摸索,也足以揭开这个话题的神秘面纱,因此您可以自己冒险进入1和0的世界,并做各种按位排列的恶作剧。
感谢您的阅读,并希望本文对您有所帮助。 您可以通过按住拍手按钮一会儿(双关语)并与可能有兴趣的朋友分享这篇文章来为我提供帮助!
用JS编程:
递归 : https : //hackernoon.com/programming-with-js-recursion-31371e2bf808
合并排序 : https : //medium.com/@KondovAlexander/programming-with-js-merge-sort-deb677b777c0
二进制搜索 : https : //medium.com/@KondovAlexander/programming-with-js-binary-search-aaf86cef9cb3
插入排序 : https : //medium.com/@KondovAlexander/programming-with-js-insertion-sort-1316df8354f5
From: https://hackernoon.com/programming-with-js-bitwise-operations-393eb0745dc4