javascript按位非运算符的使用方法


Posted in Javascript onNovember 14, 2013

~:按位非操作符由一个波浪线(~)表示,执行按位非的结果就是返回数值的反码。

var num1 = 3;    // 我的幸运数字是3
var num2 = ~(num1);
console.log(num2)  //  "-4"
var num3 = -3;  
var num4 = ~(num3);
console.log(num4)  //  "2"
console.log(~(0))  //  "-1"

没错,现在我们知道了~运算符的原理了。开心吗?。。。不开心,虽然这一章,我看过好多次。。。因为我从来就没用过,实在是惭愧啊。大家觉得这个运算符可以用在什么地方呢?恩。。。沉思一下,放一段同事的代码:
if (~item[search_key].toLowerCase().indexOf(query)) {
                        _results.push(item);
 }

代码:
if( str.indexOf(query) != -1 )  or  if( str.indexOf(query) >= 0)

原理分析:
通过str.indexOf(query)最后得出的值,无外乎不过两种:
1. str中包含query字符串,则值是0或正整数,此时:!!(~str.indexOf(query)) === true(或者这样转换 Boolean(~str.indexOf(query)) === true)
2. srt中不包含query字符串,则值为-1,此时:!!(~str.indexOf(query)) === false
因此通过加上一个~就能很好的对indexOf的查询结果进行判断了。清爽无比,从此再也没有头屑的烦恼了。。哈哈!
最后我们来分析一下效率吧,印象中位运算的效率应该比较运算符高。来段代码:
var str = "hutaoer go go go!!!!! My lucky number is 33!!";
    var query = 33;
    var timeStart1 = new Date() - 0;
    for(var i = 0; i < 100000000; i++) {
        ~str.indexOf(query)
    }
    var timeEnd1 = new Date() - 0;
    console.log('~ cost time:' + (timeEnd1 - timeStart1)); 
    // ~ cost time:9954  循环次数:10000000 
    // ~ cost time:104  循环次数: 100000
    var timeStart2 = new Date() - 0;
    for(var j = 0; j < 100000000; j++) {
        str.indexOf(query) >= 0
    }
    var timeEnd2 = new Date() - 0;
    console.log('>= cost time:' + (timeEnd2 - timeStart2)); 
   // >= cost time:10120  循环次数:10000000

程序更新:原来的测试代码在分割线上面不变。代码如下:
    var str = "hutaoer go go go!!!!! My lucky number is 33!!";
    var query = 33;
    var timeStart1 = new Date() - 0;
    for(var i = 0; i < 1000000; i++) {
        ~str.indexOf(query)
    }
    var timeEnd1 = new Date() - 0;
    console.log('~ cost time:' + (timeEnd1 - timeStart1));
    //  循环1000000次  127ms
    var timeStart2 = new Date() - 0;
    for(var j = 0; j < 1000000; j++) {
        str.indexOf(query) >= 0
    }
    var timeEnd2 = new Date() - 0;
    console.log('>= cost time:' + (timeEnd2 - timeStart2));
    // 循环1000000次 101ms
    var timeStart3 = new Date() - 0;
    for(var k = 0; k < 1000000; k++) {
        Boolean(~str.indexOf(query))
    }
    var timeEnd3 = new Date() - 0;
    console.log('add Boolean cost time:' + (timeEnd3 - timeStart3));
    // 循环1000000次 129ms
    var timeStart4 = new Date() - 0;
    for(var k = 0; k < 1000000; k++) {
        !!(~str.indexOf(query))
    }
    var timeEnd4 = new Date() - 0;
    console.log('add !! cost time:' + (timeEnd4 - timeStart4));
    // 循环10000000次 103ms
   

其实,对于一次运算本身来说,相差无几,只是在循环次数过大,比如超过了10000000次,效率才会有一些差距。
【更新 2013.10.27 17:28】通过修改后的测试,我们可以发现,“按位非”这中写法也许并非是效率最高的,表现最好的居然是我以前常用的写法,采用比较运算符。这确实让我很吃惊。有时候,人往往容易被常识,表象所迷惑,但亲自去尝试后,或许会有不一样的发现或得出其他的结果。今天,我算吸取教训了。
在评论中,同学们都比较反对这种非常见的写法,毕竟这些技巧可能会给阅读代码的同学造成困扰。如果不知道原理的话,甚至让人费解。或许,直接用一些简单的逻辑和常见的运算符,会是更好的选择?你们觉得呢?
因此平时写代码的时候,用哪种写法都可以。但是希望我们能将这些技巧记住,关键时刻或许就能派上用场。
Javascript 相关文章推荐
JavaScript 事件对象的实现
Jul 13 Javascript
Wordpress ThickBox 点击图片显示下一张图的修改方法
Dec 11 Javascript
jquery中实现简单的tabs插件功能的代码
Mar 02 Javascript
详细解密jsonp跨域请求
Apr 15 Javascript
JQuery的Pager分页器实现代码
May 03 Javascript
Vue中如何实现轮播图的示例代码
Jul 27 Javascript
详解RequireJs官方使用教程
Oct 31 Javascript
Vue项目查看当前使用的elementUI版本的方法
Sep 27 Javascript
微信小程序实现选项卡效果
Nov 06 Javascript
详解React 元素渲染
Jul 07 Javascript
vue 动态创建组件的两种方法
Dec 31 Vue.js
一文搞懂redux在react中的初步用法
Jun 09 Javascript
javascript Array.prototype.slice的使用示例
Nov 14 #Javascript
js取消单选按钮选中示例代码
Nov 14 #Javascript
js实现目录定位正文示例
Nov 14 #Javascript
通过action传过来的值在option获取进行验证的方法
Nov 14 #Javascript
javascript间隔刷新的简单实例
Nov 14 #Javascript
Enter转换为Tab的小例子(兼容IE,Firefox)
Nov 14 #Javascript
js中prototype用法详细介绍
Nov 14 #Javascript
You might like
PHP实现基于PDO扩展连接PostgreSQL对象关系数据库示例
2018/03/31 PHP
Laravel 5.1 框架Blade模板引擎用法实例分析
2020/01/04 PHP
JQuery的ajax获取数据后的处理总结(html,xml,json)
2010/07/14 Javascript
上传的js验证(图片/文件的扩展名)
2013/04/25 Javascript
当jQuery1.7遇上focus方法的问题
2014/01/26 Javascript
js实现分享到随页面滚动而滑动效果的方法
2015/04/10 Javascript
jQuery 更改checkbox的状态,无效的解决方法
2016/07/22 Javascript
jQuery实现搜索页面关键字的功能
2017/02/16 Javascript
vue-router单页面路由
2017/06/17 Javascript
微信小程序模板和模块化用法实例分析
2017/11/28 Javascript
JavaScript+H5实现微信摇一摇功能
2018/05/23 Javascript
vue 组件中添加样式不生效的解决方法
2018/07/06 Javascript
Nodejs监听日志文件的变化的过程解析
2019/08/04 NodeJs
JS apply用法总结和使用场景实例分析
2020/03/14 Javascript
React.js组件实现拖拽排序组件功能过程解析
2020/04/27 Javascript
JavaScript实现手机号码 3-4-4格式并控制新增和删除时光标的位置
2020/06/02 Javascript
vue+element-ui表格封装tag标签使用插槽
2020/06/18 Javascript
对python中的logger模块全面讲解
2018/04/28 Python
解决sublime+python3无法输出中文的问题
2018/12/12 Python
Python实现i人事自动打卡的示例代码
2020/01/09 Python
Django 项目布局方法(值得推荐)
2020/03/22 Python
python如何保存文本文件
2020/06/07 Python
keras-siamese用自己的数据集实现详解
2020/06/10 Python
谈谈python垃圾回收机制
2020/09/27 Python
html5指南-2.如何操作document metadata
2013/01/07 HTML / CSS
英国轻奢珠宝品牌:Astley Clarke
2016/12/18 全球购物
Looking4Parking美国:全球排名第一的机场停车比较品牌
2019/08/26 全球购物
Yahoo-PHP面试题4
2012/05/05 面试题
自我评价优秀范文分享
2013/11/30 职场文书
化学实验员岗位职责
2013/12/28 职场文书
分公司总经理岗位职责
2014/08/03 职场文书
工作粗心大意检讨书
2014/09/18 职场文书
停车位租赁协议书
2014/09/24 职场文书
谢师宴邀请函
2015/02/02 职场文书
护士医德考评自我评价
2015/03/03 职场文书
MySQL单表千万级数据处理的思路分享
2021/06/05 MySQL