JavaScript对象作为哈希?复杂性是否大于O(1)?

Par*_*ris 51 javascript performance

对于我最近写的一些算法,我认为哈希会非常好.我认为我可能只是使用对象中的成员变量作为键值对.我不确定这是否是最佳的,因为我真的不知道幕后发生了什么.我还假设V8与其他环境的不同之处.但我想,查找成员变量会非常快(希望如此)?

总而言之,我想知道在JavaScript对象中编写,读取,创建和删除成员变量的运行时复杂性是否都是O(1).如果环境存在差异(v8与其他相比),它们是什么?

Par*_*ris 58

更新
Chrome的删除现在非常快!但是,当您接近100万个密钥时,更新似乎会变慢.

好吧,我有一些数据.我要说是的浏览器之间存在差异.似乎不同的环境关心不同的CRUD操作.此外,对象是引擎盖下的哈希值,因为当键数增加时性能不受影响.如果3个测试之间没有性能差异(ops/sec),那么(我认为)这意味着它是一个散列,并且每个操作的复杂性都是O(1),无论它与其他操作相比是更快还是更慢.换句话说,如果任何测试的操作/秒计数发生变化,因为密钥增加,那么它不是O(1)(事实并非如此).

测试:
http://jsperf.com/objectsashashes/2(100键)
http://jsperf.com/objectsashashes/3 (100k键)
http://jsperf.com/objectsashashes/(100万键)
http:/ /jsperf.com/objects-as-hashes-300-mil(10m键)

观察:

  • 创建对的时间是10密耳键值对的线性.
  • Chrome:针对读取进行了优化.创建和更新有点慢.
  • Safari:针对写入进行了优化,但读取速度相当快.似乎更慢更新它.
  • IE9:不赞成任何操作.删除会略微提高性能.注意:我使用旧机器进行测试.
  • IE10:删除会略微提高性能.创建/更新比阅读慢.
  • IE8:无法测试,但最新的win7更新似乎IE9自动安装.关于XP机器不确定.
  • Firefox:极度优化读取.其他一切都差不多.
  • Opera:所有操作都以相同的速度运行.
  • 存储的最大密钥的唯一限制似乎是基于内存(浏览器,环境或机器强制执行)

最后的注意事项:
虽然hash ['something']并不比hash.something慢,但是如果你需要连接以找到你的哈希的名字,你的性能会大大降低(http://jsperf.com/member-associative-array- syntax-vs-dot-syntax),这就是我在上面的性能测试之外缓存这些值的原因.如果可能,请避免连接.字符串在JS中是不可变的,因此每个连接创建3个对象/"基元"(字符串1,字符串2和连接字符串).

  • 它可能不会影响您的统计信息,但在拆解功能中,"n"未定义.您指定了一个全局但jsPerf已将代码包装在函数中.所以函数(如果被调用)抛出一个似乎被jsPerf忽略的错误. (2认同)

Mat*_*all 10

JavaScript对象哈希值.我无法想象任何不能在对象属性上提供常量CRUD操作的理智实现.

您是否看到此方法的具体性能问题?

  • 根据鸽子原则,在降低性能之前,您可以拥有的成员变量数量存在有限的上限(例如,由于哈希冲突).但是,除非你故意挑选病态上不好的对象密钥,并使用大量密钥,否则你不会看到这种退化. (4认同)
  • 我发布了我的分析结果!再次感谢! (2认同)