解决遍历时Array.indexOf产生的性能问题

复制代码 代码如下:

  Ext.applyIf(Array.prototype, {

  /**

  * Checks whether or not the specified object exists in the array.

  * @param {Object} o The object to check for

  * @param {Number} from (Optional) The index at which to begin the search

  * @return {Number} The index of o in the array (or -1 if it is not found)

  */

  indexOf : function(o, from){

  var len = this.length;

  from = from || 0;

  from += (from < 0) ? len : 0;

  for (; from < len; ++from){

  if(this[from] === o){

  return from;

  }

  });

  return -1;

  }

  从源码可以看出,查找是简单的线性查找。

  由于线性查找效率是 O(n) ,所以,在数据量稍大的时候,需要寻找替代 Array 的办法。有很多文章说过关于 Array 的这个问题,包括《权威指南》,办法是模拟一个 Hash 表。

  下面是有问题的代码

  

复制代码 代码如下:

  var hostsIP = [];

  Ext.each(_this.hosts,function(item){

  hostsIP.push(item.ip);

  });

  Ext.each(txtHostsIP,function(ip){

  if(hostsIP.indexOf(ip)===-1){//问题代码

  var host = {

  isAppend : true,//新增的主机

  isAgentOk : false,

  ip : ip

  };

  _this.hosts.push(

  Ext.apply(host,_this.MAPPING_FIELDS)

  );

  isAppend = true;

  }else{

  errors.push('IP['+ip+']已存在');

  }

  });

  当hostsIP长度超过2000个时,IE8-浏览器会出现如下提示

  

解决遍历时Array.indexOf产生的性能问题

按照《权威指南》中给出的提示,我对代码做了如下修改后,问题解决。

  

复制代码 代码如下:

  var hostsIP = {};

  Ext.each(_this.hosts,function(item){

  hostsIP[item.ip]=item.ip;

  });

  Ext.each(txtHostsIP,function(ip){

  if(!hostsIP.hasOwnProperty(ip)){

  var host = {

  isAppend : true,//新增的主机

  isAgentOk : false,

  ip : ip

  };

  _this.hosts.push(

  Ext.apply(host,_this.MAPPING_FIELDS)

  );

  isAppend = true;

  }else{

  errors.push('IP['+ip+']已存在');

  }

  });