свойство вычисляемого объекта, дающее результат, отличный от точечной нотации - PullRequest
0 голосов
/ 14 января 2020

Я использую функцию сортировки слиянием. Когда я использую точечную запись для свойства, которое я пытаюсь использовать, он сортирует их правильно. Я решил, что хочу иметь возможность повторно использовать функцию сортировки в других свойствах, поэтому я решил сделать свойство аргументом в функции, а не жестко его кодировать. Проблема в том, что когда я передал ему одно и то же свойство, элементы сортировались по-разному. Не уверен, почему это происходит.

Вот массив объектов, которые я сортирую на основе свойства "points".

[ { teamNum: 0, points: 2, GD: -2, goals: 3, rank: 0 },
  { teamNum: 1, points: 2, GD: -2, goals: 3, rank: 0 },
  { teamNum: 2, points: 1, GD: -3, goals: 2, rank: 0 },
  { teamNum: 3, points: 4, GD: 1, goals: 4, rank: 0 },
  { teamNum: 4, points: 5, GD: 4, goals: 5, rank: 0 },
  { teamNum: 5, points: 4, GD: 2, goals: 6, rank: 0 } ]

рабочая функция сортировки слиянием:

* обратите внимание на .points в , если оператор слияния

  function mergeSort(arr){
   var len = arr.length;
   if(len <2)
      return arr;
   var mid = Math.floor(len/2),
       left = arr.slice(0,mid),
       right =arr.slice(mid);
   //send left and right to the mergeSort to break it down into pieces
   //then merge those
   return merge(mergeSort(left),mergeSort(right));
}


function merge(left, right){
  var result = [],
      lLen = left.length,
      rLen = right.length,
      l = 0,
      r = 0;
  while(l < lLen && r < rLen){
     if(left[l].points < right[r].points){
       result.push(left[l++]);
     }
     else{
       result.push(right[r++]);
    }
  }  
  //remaining part needs to be addred to the result
  return result.concat(left.slice(l)).concat(right.slice(r));
}

дает мне ожидаемый результат:

let rankArr = mergeSort(Teams).reverse();
console.log(rankArr);
//outputs:

[ { teamNum: 4, points: 5, GD: 4, goals: 5, rank: 0 },
  { teamNum: 3, points: 4, GD: 1, goals: 4, rank: 0 },
  { teamNum: 5, points: 4, GD: 2, goals: 6, rank: 0 },
  { teamNum: 0, points: 2, GD: -2, goals: 3, rank: 0 },
  { teamNum: 1, points: 2, GD: -2, goals: 3, rank: 0 },
  { teamNum: 2, points: 1, GD: -3, goals: 2, rank: 0 } ]

const Teams = [ { teamNum: 0, points: 2, GD: -2, goals: 3, rank: 0 },
  { teamNum: 1, points: 2, GD: -2, goals: 3, rank: 0 },
  { teamNum: 2, points: 1, GD: -3, goals: 2, rank: 0 },
  { teamNum: 3, points: 4, GD: 1, goals: 4, rank: 0 },
  { teamNum: 4, points: 5, GD: 4, goals: 5, rank: 0 },
  { teamNum: 5, points: 4, GD: 2, goals: 6, rank: 0 } ]
  
function mergeSort(arr) {
  var len = arr.length;
  if (len < 2)
    return arr;
  var mid = Math.floor(len / 2),
    left = arr.slice(0, mid),
    right = arr.slice(mid);
  //send left and right to the mergeSort to break it down into pieces
  //then merge those
  return merge(mergeSort(left), mergeSort(right));
}


function merge(left, right) {
  var result = [],
    lLen = left.length,
    rLen = right.length,
    l = 0,
    r = 0;
  while (l < lLen && r < rLen) {
    if (left[l].points < right[r].points) {
      result.push(left[l++]);
    } else {
      result.push(right[r++]);
    }
  }
  //remaining part needs to be addred to the result
  return result.concat(left.slice(l)).concat(right.slice(r));
}
let rankArr = mergeSort(Teams).reverse();
console.log(rankArr);

Вот сортировка слияния с динамическим c свойством

  function mergeSort(arr, prop){
   var len = arr.length;
   if(len <2)
      return arr;
   var mid = Math.floor(len/2),
       left = arr.slice(0,mid),
       right =arr.slice(mid);
   //send left and right to the mergeSort to break it down into pieces
   //then merge those
   return merge(mergeSort(left),mergeSort(right), prop);
}


function merge(left, right, prop){
  var result = [],
      lLen = left.length,
      rLen = right.length,
      l = 0,
      r = 0;
  while(l < lLen && r < rLen){
     if(left[l][prop] < right[r][prop]){
       result.push(left[l++]);
     }
     else{
       result.push(right[r++]);
    }
  }  
  //remaining part needs to be addred to the result
  return result.concat(left.slice(l)).concat(right.slice(r));
}

//invoked
  let rankArr = mergeSort(Teams,"points").reverse();

Выходы:

[ { teamNum: 3, points: 4, GD: 1, goals: 4, rank: 0 },
  { teamNum: 4, points: 5, GD: 4, goals: 5, rank: 0 },
  { teamNum: 5, points: 4, GD: 2, goals: 6, rank: 0 },
  { teamNum: 0, points: 2, GD: -2, goals: 3, rank: 0 },
  { teamNum: 1, points: 2, GD: -2, goals: 3, rank: 0 },
  { teamNum: 2, points: 1, GD: -3, goals: 2, rank: 0 } ]

const Teams = [ { teamNum: 0, points: 2, GD: -2, goals: 3, rank: 0 },
  { teamNum: 1, points: 2, GD: -2, goals: 3, rank: 0 },
  { teamNum: 2, points: 1, GD: -3, goals: 2, rank: 0 },
  { teamNum: 3, points: 4, GD: 1, goals: 4, rank: 0 },
  { teamNum: 4, points: 5, GD: 4, goals: 5, rank: 0 },
  { teamNum: 5, points: 4, GD: 2, goals: 6, rank: 0 } ]
  
function mergeSort(arr, prop) {
  var len = arr.length;
  if (len < 2)
    return arr;
  var mid = Math.floor(len / 2),
    left = arr.slice(0, mid),
    right = arr.slice(mid);
  //send left and right to the mergeSort to break it down into pieces
  //then merge those
  return merge(mergeSort(left), mergeSort(right), prop);
}


function merge(left, right, prop) {
  var result = [],
    lLen = left.length,
    rLen = right.length,
    l = 0,
    r = 0;
  while (l < lLen && r < rLen) {
    if (left[l][prop] < right[r][prop]) {
      result.push(left[l++]);
    } else {
      result.push(right[r++]);
    }
  }
  //remaining part needs to be addred to the result
  return result.concat(left.slice(l)).concat(right.slice(r));
}

//invoked
console.log(mergeSort(Teams, "points").reverse());

Ответы [ 2 ]

1 голос
/ 14 января 2020

Ваша динамика c mergeSort требует второго аргумента, prop. При первоначальном вызове аргумент передается правильно:

let rankArr = mergeSort(Teams,"points").reverse();

Но вам также необходимо передать его рекурсивному вызову. Измените

return merge(mergeSort(left),mergeSort(right), prop);

на

return merge(mergeSort(left, prop),mergeSort(right, prop), prop);

, в противном случае во время рекурсии это будет undefined, и никакой разумной сортировки не произойдет.

const Teams = [ { teamNum: 0, points: 2, GD: -2, goals: 3, rank: 0 },
  { teamNum: 1, points: 2, GD: -2, goals: 3, rank: 0 },
  { teamNum: 2, points: 1, GD: -3, goals: 2, rank: 0 },
  { teamNum: 3, points: 4, GD: 1, goals: 4, rank: 0 },
  { teamNum: 4, points: 5, GD: 4, goals: 5, rank: 0 },
  { teamNum: 5, points: 4, GD: 2, goals: 6, rank: 0 } ];

function mergeSort(arr, prop){
   var len = arr.length;
   if(len <2)
      return arr;
   var mid = Math.floor(len/2),
       left = arr.slice(0,mid),
       right =arr.slice(mid);
   //send left and right to the mergeSort to break it down into pieces
   //then merge those
   return merge(mergeSort(left, prop),mergeSort(right, prop), prop);
}


function merge(left, right, prop){
  var result = [],
      lLen = left.length,
      rLen = right.length,
      l = 0,
      r = 0;
  while(l < lLen && r < rLen){
     if(left[l][prop] < right[r][prop]){
       result.push(left[l++]);
     }
     else{
       result.push(right[r++]);
    }
  }  
  //remaining part needs to be addred to the result
  return result.concat(left.slice(l)).concat(right.slice(r));
}

//invoked
  let rankArr = mergeSort(Teams,"points").reverse();
  console.log(rankArr);
0 голосов
/ 14 января 2020

Вы можете просто сделать:

var arrayOfObjs = [ { teamNum: 0, points: 2, GD: -2, goals: 3, rank: 0 },
  { teamNum: 1, points: 2, GD: -2, goals: 3, rank: 0 },
  { teamNum: 2, points: 1, GD: -3, goals: 2, rank: 0 },
  { teamNum: 3, points: 4, GD: 1, goals: 4, rank: 0 },
  { teamNum: 4, points: 5, GD: 4, goals: 5, rank: 0 },
  { teamNum: 5, points: 4, GD: 2, goals: 6, rank: 0 } ];
var sorted = arrayOfObjs.slice();
sorted.sort(function(a, b){
  return b.points-a.points;
});
console.log(sorted);
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...