Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/378.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript 如何根据优先级对不同类型的数据进行排序?_Javascript_Algorithm_Sorting - Fatal编程技术网

Javascript 如何根据优先级对不同类型的数据进行排序?

Javascript 如何根据优先级对不同类型的数据进行排序?,javascript,algorithm,sorting,Javascript,Algorithm,Sorting,我正在根据对象中存储的变量对对象列表进行排序。将该变量命名为“sortCriteria” 不同对象的“sortCriteria”值示例集: 400329529,“String1”,678,“String2”,588,“String3”,“String1”,201,“String2” 因此,基本上我可以在“sortCriteria”中获得4种值: 1.数值 2.String1 3.String2 4.String3 现在我必须对这些数据进行排序,使数字数据具有最高优先级,然后是“String1”,

我正在根据对象中存储的变量对对象列表进行排序。将该变量命名为“sortCriteria”
不同对象的“sortCriteria”值示例集:

400329529,“String1”,678,“String2”,588,“String3”,“String1”,201,“String2”

因此,基本上我可以在“sortCriteria”中获得4种值:
1.数值
2.String1
3.String2
4.String3

现在我必须对这些数据进行排序,使数字数据具有最高优先级,然后是“String1”,然后是“String2”,然后是“String3”。i、 e.
(数字>字符串1>字符串2>字符串3)的优先级
请注意,在输出中,所有这些数值都应按顺序排序。

因此,样本数据的排序顺序为- 201、329、400、529、588、678,“String1”、“String1”、“String2”、“String2”、“String3”
此外,如果多个对象具有相同的“sortCriteria”值,则应保留其顺序
例如
假设我得到了两个“sortCriteria”值相同的对象 对象1:205, 对象2:205。 然后,按排序顺序,Object1应位于Object2之前


我当前的排序特定逻辑的Javascript实现如下所示:

function mySortRule(a, b) {
         var value1 = a[1], value2 = b[1];
         var value1Priority = getPriorityOf(value1);
         var value2Priority = getPriorityOf(value2);
         return value1Priority - value2Priority;
}
function getPriorityOf(value) {
         var priority;
         if(value!="String1" && value!="String2" && value!="String3") {
             priority = value;
         }
         else if(value == "String1") {
            priority = Number.MAX_VALUE-2;
         }
         else if(value == "String2") {
            priority = Number.MAX_VALUE-1;
         }
         else if(value == "String3") {
            priority = Number.MAX_VALUE;
         }
         return priority;
}
sortCriteriaArray.sort(mySortRule);
sortCriteriaArray[i]值的格式如下: [“indexOfObject”、“sortCriteria”]

这个解决方案是可行的,但它没有保留对象的顺序。此外,我认为这不是一个好方法,因为-
1.明天,假设我们必须安装一些其他类型的弦。在这种情况下,我们必须在getPriorityOf()函数中更改这些条件语句。
2.在我看来,使用“Number.MAX_VALUE”设置优先级似乎有点不妥

有没有更好的方法来实现这一点?

看看我的解决方案,并检查它是否适合:

//数组
const arr=[400329529,“String1”,678,“String2”,588,“String3”,“String1”,201,“String2”];
//过滤方法
常量isNumber=(项目)=>!伊斯南(项目1);
const checkString=(str)=>(item)=>item==str;
//排序/配置方法
常量排序优先级=()=>{
返回[
…arr.filter(isNumber).sort((a,b)=>a-b),
…arr.filter(检查字符串(“String1”),
…arr.filter(检查字符串(“String2”)),
…arr.filter(检查字符串(“String3”),
]
}

log(sortPriority())将比较测试安排为字典式的,首先是类型(分配优先级索引,如like number:0,string:1),然后是值(如果是关系)。这是干净和可扩展的

要保留顺序,需要使用稳定的排序算法,如MergeSort


或者,如果您不打算添加其他类型,请按以下步骤进行:

  • 扫描列表并(稳定地)拆分一个子列表中的数字和另一个子列表中的字符串

  • 对子列表进行排序并将其关联


如果字符串数量较少且固定,则可以使用对象作为优先级字典而不是
getPriorityOf
来构建复合排序规则,这样就不必使用
MAX\u值。您可以按照给定字符串的顺序或默认值0(假设数字是最高优先级)获取对象,然后按数值排序

var data=[400329529,“String1”,678,“String2”,588,“String3”,“String1”,201,“String2”],
顺序={String1:1,String2:2,String3:3};
排序((a,b)=>(顺序[a]| 0)-(顺序[b]| 0)| a-b);
控制台日志(数据)
。作为控制台包装{最大高度:100%!重要;顶部:0;}

(假设每个数组元素都不是null或未定义)

检查类型。如果两者都是数字或字符串,则使用常规比较(
“String1”<“String2”
这是按字母顺序排序的)。否则,最低的是数字。您不能将数字(正32位,作为数组的索引)作为键对对象进行排序,只要这些数字不按顺序排列。为什么这没有帮助?为了简单起见,我喜欢这段代码,但是
Array.sort的规范需要使用稳定的算法吗?这似乎是OP抱怨的问题,但这正是OP抱怨的问题之一“而且,如果多个对象具有相同的“sortCriteria”值,则应保留它们的顺序。”并且“此解决方案可以正常工作,但不保留对象顺序。”换句话说,我是否正确地理解了这个答案并没有真正涵盖OP的实际问题?就我阅读的问题而言,OP已经有了一个有效的代码,但有两件事他不喜欢:1。结果排序不稳定2。该代码不是未来的证明。我说得对吗?你说的是第2个地址,但根本不说第1个地址?请看第二节。@Cid我的错,修正了。Thx,Mate是的,我觉得这个更干净。我要用这个。谢谢
function mySortRule(a, b) {
    function getPriorityOf(value) {
        // priority order..
        return [Boolean, Number, String, Array, Object, Function]
            .reverse().indexOf(value.constructor);
    }
    // smallest first..
    return getPriorityOf(a) == getPriorityOf(b) ?
        (a.valueOf() == b.valueOf() ?
            0 :
            (a.valueOf() > b.valueOf() ? 1 : -1)) :
        getPriorityOf(b) - getPriorityOf(a)
}
var sortCriteriaArray = 
    [400, 329, 529, "String1", 678, "String2", 588, "String3", "String1", 201, "String2"];
sortCriteriaArray.sort(mySortRule);
// -> [201, 329, 400, 529, 588, 678, "String1", "String1", "String2", "String2", "String3"]