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

优化使用二分查找的Climbing Leaderboard代码执行时长

优化大规模排行榜爬取算法的性能问题

需求:基于排行榜(ranked)数组与玩家分数(player)数组生成玩家排名数组。现有代码功能正常,但处理包含20万条元素的大规模ranked数组时会超时,寻求优化方案,无需提供可直接复制的代码。

现有代码

int* climbingLeaderboard(int ranked_count, int* ranked, int player_count, int* player, int* result_count) {
    
    *result_count=player_count;
    // remove duplicates
    int removed=0;
    for(int i=0, j=1; i<ranked_count-removed; i++, j++){   
      if(ranked[i]==ranked[j]){
        for(int k=j; k<ranked_count-removed; k++) 
           ranked[k]=ranked[k+1]; 
        removed++;
      }
    }
    int newsize=ranked_count-removed;
    // create an array to store ranks then fill it
    int* positions=malloc(newsize*sizeof(int));
    positions[0]=1;
    for(int i=0, j=1; j<newsize; i++, j++){
        positions[j]=(ranked[j]<ranked[i])? (positions[i]+1) : positions[i];
    }
    // create and fill the results array using binary search
    int* res = malloc(player_count*sizeof(int));
    int start=0, end=newsize-1, middle=(start+end)/2;
    int j, k=newsize-1;
    for(int i=0; i<player_count; i++){
        if(i>0&&player[i]==player[i-1]){
            *(res+i)=(*(res+(i-1))); 
            continue;
        }
        if(player[i]>=ranked[middle]){
            *(res+i)=positions[middle]; 
            j=middle-1;
            while(j>=0){
                if(player[i]>=ranked[j]) 
                    *(res+i)=positions[j];
                else if(j==k) 
                    *(res+i)=positions[j]+1; 
                else break; 
                --j;
            }
            start=0; end=middle-1;
        }
        else{
            *(res+i)=positions[newsize-1]+1; 
            j=newsize-1;
            while(j>=middle){
                if(player[i]>=ranked[j]) 
                    *(res+i)=positions[j];
                else if(j==k) 
                    *(res+i)=positions[j]+1; 
                else break; 
                --j;
            }
            start=middle+1; end=newsize-1;
        }
        middle=(start+end)/2;
    }
    free(positions);
    return res;
}

优化方向

  • 去重逻辑优化:原去重采用嵌套循环+元素平移的方式,时间复杂度为O(n²),大规模数据下开销极大。改为一次遍历构建去重后的新数组,仅需O(n)时间,避免频繁移动数组元素的操作。
  • 排名计算合并:将排名数组(positions)的生成与去重步骤合并,在构建去重数组的同时直接计算每个位置的排名,减少一次单独遍历的开销。
  • 二分查找逻辑修复:原代码的二分查找后附加了线性扫描,没有发挥二分查找O(logn)的优势。实现完整的二分查找,精准定位玩家分数在去重排行榜中的位置,直接映射到对应排名,无需后续线性遍历。此外,若玩家分数数组是递增有序的,可以利用该特性,保持二分查找的指针不重置,或从排行榜末尾反向遍历,进一步降低查找次数。
  • 内存精简:若允许修改原ranked数组,可直接在原数组上完成去重操作,避免额外的内存分配;或者取消单独的positions数组,直接在去重后的排行榜数组中存储对应排名,减少内存占用与访问开销。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.02 03:05:48