简体   繁体   English

按3个属性对javascript数组进行排序

[英]Sorting javascript array by 3 properties

I have an array with a list of locations. 我有一个带有位置列表的数组。

I am adding on 3 properties detailing where each location is in relation to a set start location. 我要添加3个属性,详细说明每个位置相对于设置的开始位置的位置。

Each location in the array has the following 3 properties: 数组中的每个位置具有以下3个属性:

bearing (0 to 360 degrees)
humanFriendlyCompassHeading (North, North East, East etc)
distance (in km)

I am able to sort the array by bearing so the locations are listed from 0 to 360 degrees and the human friendly compass headings are in order so the first few entries in the array are North, followed by NorthEast, East etc. 我可以通过方位对数组进行排序,以便将位置从0到360度列出,并且人性化的罗盘标题也应如此排列,以便数组中的前几个条目是North,然后是NorthEast,East等。

However, I would like the distances to be then sorted from nearest to furthest away for each human friendly compass heading ie North, NorthEast, East. 但是,我希望对于每个人类友好的指南针方向(即北,东北,东),从最近到最远的距离进行排序。

This is what I have so far using the code provided below and the comparison function: 到目前为止,这是我使用下面提供的代码和比较功能得到的结果:

var myCmp = composeComparisons([sortArrayByBearing, sortArrayByHumanFriendlyCompassHeading, sortArrayByDistance]);
res.geonames.sort(myCmp);


function sortArrayByDistance(A, B)
{
return parseFloat(A.distance) - parseFloat(B.distance);
}

function sortArrayByBearing(A, B)
{
return parseFloat(A.bearing) - parseFloat(B.bearing);
}

//Used to sort results array by humanFriendlyCompassHeading
//usage: results.sort(sortArrayByHumanFriendlyCompassHeading);
//The sorting of humanFriendlyCompassHeading is realised with a map and look up for the value.
function sortArrayByHumanFriendlyCompassHeading(A, B) {
var DIRECTIONS = { North: 0, NorthEast: 1, East: 2, SouthEast: 3, South: 4, SouthWest: 5, West: 6, NorthWest: 7};
return         DIRECTIONS[A.humanFriendlyCompassHeading] - DIRECTIONS[B.humanFriendlyCompassHeading];
}

Here is a sample output of how I would like the data to be sorted: 这是我希望如何对数据进行排序的示例输出:

  • (514m, North) Nottingham Trent University, School of Art and Design (北514m)诺丁汉特伦特大学艺术与设计学院

  • (695m, North) The Arboretum, Nottingham (北部695m)诺丁汉植物园

  • (424m, NorthEast) Archiam Centre (东北424m)Archiam中心

  • (497m, NorthEast) Shakespeare Street Wesleyan Reform Chapel (东北497m)莎士比亚街卫斯理改革教堂

  • (795m, NorthEast) Nottingham Urban Area (东北(795m)诺丁汉市区

  • (796m, NorthEast) Victoria bus station, Nottingham (796m,东北)维多利亚汽车站,诺丁汉

  • (438m, East) Nottingham Conference Centre (东部438m)诺丁汉会议中心

This is part of the original array. 这是原始数组的一部分。 I am adding on the bearing, distance and human friendly values from my start location later on using the lat and lng values returned in the array: 稍后,我将使用数组中返回的lat和lng值从起始位置添加方位角,距离和人性化值:

         "summary":"The Diocese of Nottingham, England, is a Roman Catholic diocese of the Latin Rite which covers an area of 13,074 km², taking in the counties of Nottinghamshire (excluding the district of Bassetlaw), Leicestershire, Derbyshire, Rutland and Lincolnshire (...)",
     "elevation":65,
     "lng":-1.1572,
     "distance":"0.0685",
     "countryCode":"GB",
     "rank":84,
     "lang":"en",
     "title":"Roman Catholic Diocese of Nottingham",
     "lat":52.9545,
     "wikipediaUrl":"en.wikipedia.org/wiki/Roman_Catholic_Diocese_of_Nottingham"
  },
  {  
     "summary":"The Cathedral Church of St. Barnabas in the city of Nottingham, England, is a cathedral of the Roman Catholic church. It is the mother church of the Diocese of Nottingham and seat of the Bishop of Nottingham. (...)",
     "elevation":67,
     "feature":"landmark",
     "lng":-1.15708,
     "distance":"0.0703",
     "countryCode":"GB",
     "rank":82,
     "lang":"en",
     "title":"Nottingham Cathedral",
     "lat":52.95466,
     "wikipediaUrl":"en.wikipedia.org/wiki/Nottingham_Cathedral"
  },
  {  
     "summary":"The Albert Hall, Nottingham, is a City Centre Conference and Concert venue, situated in Nottingham, England. (...)",
     "elevation":61,
     "feature":"landmark",
     "lng":-1.1563944444444442,
     "distance":"0.1217",
     "countryCode":"GB",
     "rank":72,
     "lang":"en",
     "title":"Albert Hall, Nottingham",
     "lat":52.95441944444445,
     "wikipediaUrl":"en.wikipedia.org/wiki/Albert_Hall%2C_Nottingham"
  },
  {  
     "summary":"The Nottingham Playhouse is a theatre in Nottingham, Nottinghamshire, England. It was first established as a repertory theatre in the 1950s when it operated from a former cinema. Directors during this period included Val May and Frank Dunlop (...)",
     "elevation":67,
     "feature":"landmark",
     "lng":-1.1577,
     "distance":"0.1235",
     "countryCode":"GB",
     "rank":77,
     "lang":"en",
     "title":"Nottingham Playhouse",
     "lat":52.9537,
     "wikipediaUrl":"         en.wikipedia.org/wiki/Nottingham_Playhouseenter code here

To compose comparison functions for use with Array.prototype.sort , you can use a function such as this one: Array.prototype.sortArray.prototype.sort一起使用的比较函数,可以使用如下函数:

function composeComparisons(cmpFunctions) {
     return function (a, b) {
          for (var i = 0, result; i < cmpFunctions.length; i++) {
                result = cmpFunctions[i](a, b);
                if (result) {
                    return result;
                }
          }
          return 0;
     }
};

It will return a function that compares items with each of your comparison function until a significant result is obtained. 它将返回一个将项目与每个比较函数进行比较的函数,直到获得明显的结果为止。

You'd use it like that: 您可以这样使用它:

// From most significant to least significant comparison function
var myCmp = composeComparisons([cmpByBearing, cmpByDistance, cmpByFriendliness]);

array.sort(myCmp);

As a reminder, a comparison function cmp(a, b) returns a positive number if a is greater than b , a negative number if b is greater than a , and 0 if items are the same. 作为提醒,比较功能cmp(a, b)返回一个正数,如果a大于b ,负数如果b大于a ,和0如果项是相同的。

Your supposed sorting order 您应该的排序顺序

  • bearing (0 to 360 degrees) [no data here] 方位角(0到360度)[此处无数据]
  • humanFriendlyCompassHeading 人类友好指南针标题
  • distance (in metres) 距离(以米为单位)

can be realised with sorting with the following function. 可以通过以下功能进行排序。

The function takes for every sorting group the difference and if it is the same (this is the value 0 ), then the next group is taken and sorted by the result of the difference, and so on. 该函数对每个排序组都采用差异,如果差异相同(这是值0 ),那么将采用下一个组并根据差异的结果进行排序,依此类推。

The sorting of humanFriendlyCompassHeading , (here reworded with compassDirection ) is realised with a map and look up for the value. 使用地图实现对humanFriendlyCompassHeading的排序(在此处用compassDirection改写),然后查找该值。

 var data = [ { distance: 695, compassDirection: 'North', target: 'The Arboretum, Nottingham' }, { distance: 497, compassDirection: 'NorthEast', target: 'Shakespeare Street Wesleyan Reform Chapel' }, { distance: 438, compassDirection: 'East', target: 'Nottingham Conference Centre' }, { distance: 514, compassDirection: 'North', target: 'Nottingham Trent University, School of Art and Design' }, { distance: 795, compassDirection: 'NorthEast', target: 'Nottingham Urban Area' }, { distance: 424, compassDirection: 'NorthEast', target: 'Archiam Centre' }, { distance: 796, compassDirection: 'NorthEast', target: 'Victoria bus station, Nottingham' } ]; data.sort(function (a, b) { var D = { North: 0, NorthEast: 45, East: 90, /* ... */ }; return D[a.compassDirection] - D[b.compassDirection] || a.distance - b.distance; }); document.write('<pre>' + JSON.stringify(data, 0, 4) + '</pre>'); 

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM