我认为正则表达式非常快,第三种选择令人困惑。你觉得怎么样?
http://jqfundamentals.com/book/ch09s12.html
// old way
if (type == 'foo' || type == 'bar') { ... }
// better
if (/^(foo|bar)$/.test(type)) { ... }
// object literal lookup
if (({ foo : 1, bar : 1 })[type]) { ... }
答案 0 :(得分:6)
我会谦卑地不同意丽贝卡·墨菲(Rebecca Murphey)并为简单而投票,这是第一种选择。
我认为正则表达式很快
机器代码甚至更快,但我们不使用它。
第三个选项令人困惑
如果你不熟悉这个技巧,那只会让人感到困惑。 (对于那些不习惯看正则表达式来比较两个字符串的人来说,第二个选项会更加令人困惑。)
答案 1 :(得分:5)
我刚刚做了一个基本的基准,我老实说不确定她是如何得到这些结果的...... http://jsbin.com/uzuxi4/2/edit
正则表达式似乎是最好的,但在所有现代浏览器中,第一个是迄今为止最快的。最后一个是极其缓慢的。我理解三者之间的复杂性理论,但在实践中,似乎并不正确。
更不用说第一个也具有最佳可读性的事实,它似乎也是最快的。我甚至嵌套循环来利用文字表或常量的任何浏览器缓存(无济于事)。
修改强> 看来,当明确创建一个对象时,她确实是正确的,但是:http://jsbin.com/uzuxi4/4/edit
function __hash() {
...
var type = 'bar';
var testobj = { foo : 1, bar : 1 };
var c = 0;
for (i = 0; i < 1000; i++) {
if (testobj[type]) {
for (j = 0; j < 10000; j++) {
if (testobj[type]) { c++; }
}
}
}
...
}
我们看到,一旦对象有内部参考,寻道时间就会下降到大约500毫秒,这可能是一个平台。对象键查找可能是较大数据集的最佳选择,但实际上我并不认为它是日常使用的可行选项。
答案 2 :(得分:2)
第三个选项也比其他两个选项更好地扩展,因为添加了更多替代字符串,因为前两个是O(n),第三个是平均情况下的O(1)。
如果我们想谈论哪个选项更漂亮/更易于维护,那就是一个完全独立的对话。
答案 3 :(得分:1)
第一种情况应该用===
来完成以避免任何类型强制,但是根据你需要检查它的替代数量可以变成O(N)
,但是根据你的代码大多数JS引擎将能够进行简单的指针检查以进行比较。
在第二种情况下,您使用RegExp,而RegExps非常快,对于简单的相等决策,它们往往比更直接的相等比较慢。像你这样的简单字符串比较可能是现代JS引擎中的指针比较,但是如果使用正则表达式,则regexp 必须读取每个字符。
第三种情况比较棘手 - 如果你有很多值要检查它可能会更快,特别是如果你缓存对象而不是重复重新创建它,因为它只是一个哈希查找 - 确切的性能查找取决于引擎。
我怀疑switch语句会击败对象文字案例。
出于好奇,我做了一个测试(你可以看到here),最快的方法(至少每晚在webkit中)似乎是一个switch语句,接着是if,后跟对象, regexp的最后一次。
答案 4 :(得分:1)
只是想在这里权衡一下,并提醒大家这是一本开源书籍,有许多人的贡献!实际上,正在讨论的部分是基于社区成员提供的内容。如果您有改进该部分的建议,请务必在存储库上打开一个问题,或者更好的是,分叉回购并向我发送拉取请求:)
也就是说,我刚刚设置了一个jsPerf测试(http://jsperf.com/string-tests),至少在Chrome中,结果与本书的内容相反。我已经在这本书上打开了一个问题,并将在不久的将来尝试解决这个问题。
最后,有两件事:
答案 5 :(得分:0)
使用哈希查找优化对象文字查找,只需要一次逻辑检查而不是n。在较长的列表中,您也不必重复“类型==”数万次。
答案 6 :(得分:0)
为了简单和可读性,第一次将赢得每次。它可能不会那么快,但除非它处于严重运行的循环中,否则谁会关心。
好的编译器应该优化这样的事情。