You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

基于Id高效更新数组元素值的最优方案探讨

优化基于ID的数组批量更新方案(Socket游戏场景)

哥们,我完全懂你在Socket游戏里处理高频批量更新的痛点——几百个对象每秒多次更新,原来的双重遍历肯定会拖慢性能,咱们直接上最优解:

先拆解问题:原来的性能瓶颈

你当前的update函数用array1.forEach搭配array2.find,本质是双重线性遍历,时间复杂度是O(n*m)(n是array1长度,m是array2长度)。当数组规模上去,每秒跑好几次的话,这个开销会直接影响游戏流畅度。

最优方案:用哈希映射把查找复杂度降到O(1)

核心思路是先把array2转换成以id为键的映射表,这样后续更新array1时,直接通过id就能瞬间找到对应数据,不用再反复遍历整个array2。

修改后的完整代码

JavaScript部分

var array1 = [{ id:"asd4567wds8", x: 109, y: 763 }, { id:"df567wgfdz4", x: 450, y: 132 }, { id: "cvbz5476zzg", x: 903, y: 865 }]
var array2 = [{ id:"df567wgfdz4", x: 450, y: 137 },{ id:"asd4567wds8", x: 114, y: 763 }, { id: "cvbz5476zzg", x: 908, y: 870 }]

$(document).ready(function(){
  display();
  $("#update").click(function(){
    update();
    display();
  })
})

// 优化后的update函数
function update(){
  // 先把array2转成id->数据的映射,仅需遍历一次array2
  const array2Map = {};
  array2.forEach(item => {
    array2Map[item.id] = item;
  });

  // 遍历array1,直接通过id从映射取数据更新
  array1.forEach(element => {
    const updateData = array2Map[element.id];
    if (updateData) { // 兜底判断,避免id不匹配时报错
      element.x = updateData.x;
      element.y = updateData.y;
    }
  });
}

function display(){
  $("#Array1").empty().append("Array 1: ");
  $("#Array2").empty().append("Array 2: ");
  array1.forEach(function(element){
    var p = $("<span>").text(`[${element.x}, ${element.y}] `)
    $("#Array1").append(p)
  })
  array2.forEach(function(element){
    var p = $("<span>").text(`[${element.x}, ${element.y}] `)
    $("#Array2").append(p)
  })
  if(test(array1, array2)){
    $("#test").text("Success!")
  } else {
    $("#test").text("Values do not match")
  }
}

/* Test function do not change */
function test(array1, array2){
  var clear = true;
  array1.forEach(function(element){
    var temp = array2.find(function(element2){
      return element.id === element2.id
    });
    clear = (element.x === temp.x && element.y === temp.y)?clear:false;
  });
  return clear;
}

HTML部分

<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<body>
  <div id="Array1">Array 1: </div>
  <div id="Array2">Array 2: </div>
  <button id="update"> Update </button>
  <h3 id="test"></h3>
</body>

为什么这个方案更高效?

  • 时间复杂度从O(n*m)降到O(n+m):转换映射表仅需遍历一次array2(O(m)),更新array1仅需遍历一次array1(O(n)),数据量越大,性能提升越明显。
  • 适配高频更新场景:每秒多次执行时,CPU开销会显著降低,不会因为遍历拖慢游戏帧率。

额外优化建议

如果你的游戏里array2是从Socket接收的批量数据,还可以:

  • 直接在接收数据时就转换成映射表,不用每次update都重复转换
  • 如果需要处理array2里有array1不存在的新对象,可以在update时判断并添加到array1里(根据业务需求调整)

内容的提问来源于stack exchange,提问作者Michael Sorensen

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.27 06:48:44