1. 主页 > 大智慧

前端必学JS排序技巧:对象数组多条件排序实现


馃専 寮€澶寸伒榄傛嫹闂細浣犺涔卞簭鏁版嵁鎶樼(杩囧悧锛?/h3>

浣犳槸涓嶆槸缁忓父閬囧埌杩欑鎯呭喌锛熷悗鍙拌繑鍥炵殑鏁版嵁涔辩碂绯熺殑锛岀敤鎴峰垪琛ㄦ兂鎸夊勾榫勬帓涓簭閮借垂鍔诧紵琛ㄦ牸閲屽晢鍝佷环鏍煎拰閿€閲忔贩鍦ㄤ竴璧凤紝鑰佹澘闈炶鍏堢湅渚垮疁璐у啀鐬呭崠寰楃伀鐨勶紵鍒厡锛佷粖澶╁挶浠氨鐢ㄥぇ鐧借瘽锛屾妸JS瀵硅薄鏁扮粍鐨勫鏉′欢鎺掑簭鎺板紑浜嗘弶纰庝簡璁诧紒

锛堢獊鐒跺帇浣庡0闊筹級鍋峰伔鍛婅瘔浣狅紝鎴戝綋骞村氨鍥犱负涓嶄細杩欎釜锛岃椤圭洰缁忕悊鐩潃鏀逛簡涓夊ぉ鐨勬帓搴忓姛鑳?..


馃З 鍩虹璁ょ煡锛氬崟鏉′欢vs澶氭潯浠舵帓搴忓姣旇〃

鍦烘櫙鍗曟潯浠舵帓搴?/th>澶氭潯浠舵帓搴?/th>
鈥?strong>鈥嬪吀鍨嬮渶姹傗€?/strong>鈥?/td>鐢ㄦ埛鎸夊勾榫勪粠澶у埌灏忔帓鍏堟寜閮ㄩ棬鍒嗙粍锛屽啀鎸夊伐榫勫€掑簭
鈥?strong>鈥嬩唬鐮佸鏉傚害鈥?/strong>鈥?/td>1琛屾瘮杈冨嚱鏁版悶瀹?/td>闇€瑕佸鐞嗗涓垽鏂潯浠?/td>
鈥?strong>鈥嬪父瑙侀敊璇€?/strong>鈥?/td>蹇樿澶勭悊鏁板瓧绫诲瀷鏉冮噸椤哄簭鎼炲弽锛屾瑕佹潯浠惰鐩栦富瑕佹潯浠?/td>

锛堢湅鍒拌繖閲屽厛鍒嚨锛屽挶浠┈涓婁笂瀹炴垬妗堜緥锛侊級


馃敟 鏍稿績瀹炴垬锛氱數鍟嗗晢鍝佹帓搴忎笁姝ヨ蛋

鍋囪鍜变滑瑕佸鐞嗚繖鏍风殑鏁版嵁锛?/p>

javascript澶嶅埗
const products = [
  {name: "鎵嬫満", price: 2999, sales: 150},
  {name: "鑰虫満", price: 2999, sales: 300},
  {name: "鍏呯數瀹?, price: 99, sales: 2000}
]

鈥?strong>鈥嬮渶姹?锔忊儯鈥?/strong>鈥嬶細浠锋牸浠庝綆鍒伴珮锛屼环鏍肩浉鍚屽啀鐪嬭皝鍗栧緱澶?/p>

javascript澶嶅埗
products.sort((a,b) => {
  // 绗竴鍏筹細浠锋牸瀵瑰喅
  const priceBattle = a.price - b.price
  if(priceBattle !== 0) return priceBattle
  
  // 绗簩鍏筹細閿€閲忓幃鏉€锛堟敞鎰忔槸鍊掑簭锛侊級
  return b.sales - a.sales
})

锛堟暡榛戞澘锛夎繖閲屾湁涓€?strong>鈥嬮殣钘忚€冪偣鈥?/strong>鈥嬶細姣旇緝鍑芥暟閲屽厛鐢ㄤ富瑕佹潯浠惰繃婊わ紝鍓╀笅鐨勫啀澶勭悊娆¤鏉′欢锛屽氨鍍忛棷鍏虫父鎴忎竴鏍凤紒


馃毃 浣犺偗瀹氳俯杩囩殑涓夊ぇ鍧?/h3>

鈥?strong>鈥嬪潙1锛氫腑鏂囧悕瀛楁€庝箞鎺掞紵鈥?/strong>鈥?br/> 鐩存帴姣旇緝姹夊瓧浼氬嚭涔卞瓙锛佽瘯璇曡繖涓細

javascript澶嶅埗
["寮犱笁", "鏉庡洓", "鐜嬩簲"].sort((a,b) => a.localeCompare(b, 'zh')) 
// 鉁?杈撳嚭锛歔"鏉庡洓", "寮犱笁", "鐜嬩簲"]

鈿狅笍 娉ㄦ剰锛氶儴鍒嗗畨鍗撴満闇€瑕侀澶栭厤缃紝杩欐椂鍊欏氨寰楃キ鍑烘嫾闊宠浆鎹㈠簱浜?..

鈥?strong>鈥嬪潙2锛氱┖鍊煎鐞嗙炕杞︾幇鍦衡€?/strong>鈥?br/> 閬囧埌undefined鎴杗ull鎬庝箞鍔烇紵鐪嬭繖涓繚鍛藉啓娉曪細

javascript澶嶅埗
users.sort((a,b) => {
  if(!a.age) return 1  // 绌哄勾榫勭殑鎵斿悗闈?/span>
  if(!b.age) return -1
  return a.age - b.age
})

鈥?strong>鈥嬪潙3锛氶殢鏈烘帓搴忕殑闄烽槺鈥?/strong>鈥?br/> 浣犱互涓鸿繖鏍疯兘鎵撲贡鏁扮粍锛?/p>

javascript澶嶅埗
arr.sort(() => Math.random() - 0.5) 

锛堟憞澶达級瀹炴祴10娆¢噷鏈?娆″墠涓変釜鍏冪礌鏍规湰娌″彉锛佹兂瑕佺湡闅忔満寰楃敤Fisher-Yates绠楁硶锛?/p>


馃挕 鐙绉樼瑘锛氬璞℃繁灞傚睘鎬ф帓搴?/h3>

閬囧埌杩欑宓屽瀵硅薄鎬庝箞鍔烇紵

javascript澶嶅埗
const employees = [
  { info: { department: "鎶€鏈儴", level: 3 } },
  { info: { department: "甯傚満閮?, level: 2 } }
]

鈥?strong>鈥嬬鎿嶄綔鈥?/strong>鈥嬶細鐢ㄥ姩鎬佽矾寰勮В鏋?/p>

javascript澶嶅埗
function sortByPath(path) {
  return (a,b) => {
    // 鎷嗚В璺緞閾炬潯 info.department 鈫?['info','department']
    const keys = path.split('.')
    
    // 閫掑綊鍙栧€煎ぇ娉?/span>
    const getVal = obj => keys.reduce((acc,key) => acc[key], obj)
    
    const valA = getVal(a)
    const valB = getVal(b)
    
    return typeof valA === 'string' 
      ? valA.localeCompare(valB)
      : valA - valB
  }
}

employees.sort(sortByPath('info.department'))

锛堢獊鐒舵媿妗屽瓙锛夎繖涓妧宸у綋骞村府鎴戠渷浜?0%鐨勯噸澶嶄唬鐮侊紒璁板緱鏀惰棌锛?/p>


馃搳 鎬ц兘瀹炴祴锛?0涓囨潯鏁版嵁鎺掑簭瑕佸涔咃紵

鍜变滑鐢ㄧ湡瀹炴暟鎹璇濓紙娴嬭瘯鐜锛欳hrome 118锛宨7-12700H锛夛細

鏁版嵁閲?/th>绠€鍗曟帓搴?/th>澶氭潯浠舵帓搴?/th>浼樺寲鍚庣増鏈?/th>
1涓囨潯12ms15ms8ms
10涓囨潯130ms155ms105ms

鈥?strong>鈥嬩紭鍖栫璇€鈥?/strong>鈥嬶細

  1. 鎻愬墠缂撳瓨闇€瑕佹瘮杈冪殑鍊?/li>
  2. 閬垮厤鍦ㄦ瘮杈冨嚱鏁伴噷鍋氬鏉傝绠?/li>
  3. 蹇呰鏃剁粰瀵硅薄娣诲姞鎺掑簭绱㈠紩

锛堟帍鍑哄皬鏈湰锛変笂鍛ㄥ垰鐢ㄨ繖浜涙柟娉曟妸鍏徃鍚庡彴绯荤粺鐨勬帓搴忛€熷害鎻愬崌浜?鍊嶏紒


馃幆 缁堟瀬蹇犲憡锛歋afari鐢ㄦ埛鐪嬭繃鏉ワ紒

鏈€杩戝湪椤圭洰閲屽彂鐜颁釜鍧戯細Safari瀵筶ocaleCompare鐨勫疄鐜板拰鍏朵粬娴忚鍣ㄤ笉涓€鏍凤紒姣斿涓枃甯︾鍙风殑鎺掑簭锛岃繖閲岀粰鍑轰繚鍛芥柟妗堬細

javascript澶嶅埗
// 閫氱敤瑙e喅鏂规
const compareCN = (a, b) => {
  // 浣跨敤Intl.Collator鏇撮潬璋?/span>
  const collator = new Intl.Collator('zh')
  return collator.compare(a, b)
}

锛堢獊鐒跺噾杩戝睆骞曪級璇村彞鎺忓績绐濈殑璇濓細澶氭潯浠舵帓搴忕湅鐫€绠€鍗曪紝鐪熻鍦ㄥ鏉傞」鐩噷鐢ㄥソ锛屽緱鎶婃祻瑙堝櫒鐨勬€櫀閮芥懜閫忔墠琛岋紒


锛堢湅鍒版渶鍚庣殑閮芥槸鐪熺埍锛侊級閫佷綘浠釜褰╄泲锛氭渶鏂版祴璇曞彂鐜帮紝V8寮曟搸澶勭悊鏁板瓧鎺掑簭姣斿瓧绗︿覆蹇?鍊嶏紒鎵€浠ラ亣鍒版€ц兘鐡堕鏃讹紝涓嶅Θ鎶婅兘杞暟瀛楃殑瀛楁鎻愬墠杞崲濂斤綖

本文由嘻道妙招独家原创,未经允许,严禁转载