我需要按关键字对JavaScript对象进行排序。
因此如下:
{ 'b' : 'asdsad', 'c' : 'masdas', 'a' : 'dsfdsfsdf' }
将变成:
{ 'a' : 'dsfdsfsdf', 'b' : 'asdsad', 'c' : 'masdas' }
我需要按关键字对JavaScript对象进行排序。
因此如下:
{ 'b' : 'asdsad', 'c' : 'masdas', 'a' : 'dsfdsfsdf' }
将变成:
{ 'a' : 'dsfdsfsdf', 'b' : 'asdsad', 'c' : 'masdas' }
JavaScript对象1未排序。试图对它们进行“排序”是没有意义的。如果要迭代对象的财产,可以对键进行排序,然后检索关联的值:
变量myObj={“b”:“asdsadfd”,“c”:“masdasaf”,“a”:“dsfdsfsdf”},键=[],k、 i,len;for(myObj中的k){如果(myObj.hasOwnProperty(k)){按键.按键(k);}}keys.sort();len=按键长度;对于(i=0;i<len;i++){k=键[i];console.log(k+':'+myObj[k]);}
使用Object.keys幻想的替代实现:
变量myObj={“b”:“asdsadfd”,“c”:“masdasaf”,“a”:“dsfdsfsdf”},keys=对象键(myObj),i、 len=按键长度;keys.sort();对于(i=0;i<len;i++){k=键[i];console.log(k+':'+myObj[k]);}
1不要迂腐,但没有JSON对象。
这对我有用
/**
* Return an Object sorted by it's Key
*/
var sortObjectByKey = function(obj){
var keys = [];
var sorted_obj = {};
for(var key in obj){
if(obj.hasOwnProperty(key)){
keys.push(key);
}
}
// sort keys
keys.sort();
// create new array based on Sorted Keys
jQuery.each(keys, function(i, key){
sorted_obj[key] = obj[key];
});
return sorted_obj;
};
使用lodash可以:
some_map = { 'b' : 'asdsad', 'c' : 'masdas', 'a' : 'dsfdsfsdf' }
// perform a function in order of ascending key
_(some_map).keys().sort().each(function (key) {
var value = some_map[key];
// do something
});
// or alternatively to build a sorted list
sorted_list = _(some_map).keys().sort().map(function (key) {
var value = some_map[key];
// return something that shall become an item in the sorted list
}).value();
只是思考的食物。
假设它在显示无序对象财产的VisualStudio调试器中很有用。
(function(s) {
var t = {};
Object.keys(s).sort().forEach(function(k) {
t[k] = s[k]
});
return t
})({
b: 2,
a: 1,
c: 3
});
与内联版本相同:
(function(s){var t={};Object.keys(s).sort().forEach(function(k){t[k]=s[k]});return t})({b:2,a:1,c:3})
如果有嵌套对象或嵌套数组obj,请使用此代码。
var sortObjectByKey = function(obj){
var keys = [];
var sorted_obj = {};
for(var key in obj){
if(obj.hasOwnProperty(key)){
keys.push(key);
}
}
// sort keys
keys.sort();
// create new array based on Sorted Keys
jQuery.each(keys, function(i, key){
var val = obj[key];
if(val instanceof Array){
//do for loop;
var arr = [];
jQuery.each(val,function(){
arr.push(sortObjectByKey(this));
});
val = arr;
}else if(val instanceof Object){
val = sortObjectByKey(val)
}
sorted_obj[key] = val;
});
return sorted_obj;
};
如前所述,对象是无序的。
然而
你可能会发现这个成语很有用:
var o = { 'b' : 'asdsad', 'c' : 'masdas', 'a' : 'dsfdsfsdf' };
var kv = [];
for (var k in o) {
kv.push([k, o[k]]);
}
kv.sort()
然后,您可以遍历kv并执行任意操作。
> kv.sort()
[ [ 'a', 'dsfdsfsdf' ],
[ 'b', 'asdsad' ],
[ 'c', 'masdas' ] ]
很多人都提到“对象无法排序”,但在那之后,他们给了你一个可行的解决方案。矛盾,不是吗?
没有人提及这些解决方案为何奏效。它们是这样的,因为在大多数浏览器的实现中,对象中的值是按照添加它们的顺序存储的。这就是为什么如果您从排序的键列表中创建新对象,它将返回预期结果。
我认为我们可以再增加一个解决方案——ES5功能方式:
function sortObject(obj) {
return Object.keys(obj).sort().reduce(function (result, key) {
result[key] = obj[key];
return result;
}, {});
}
上述ES2015版本(格式为“一行”):
const sortObject = o => Object.keys(o).sort().reduce((r, k) => (r[k] = o[k], r), {})
上述示例的简短解释(如评论中所要求的):
Object.keys为我们提供了所提供对象(obj或o)中的键列表,然后我们使用默认排序算法对这些键进行排序,接下来使用reduce将数组转换回对象,但这次对所有键进行了排序。
核心版本:
function order(unordered)
{
return _.object(_.sortBy(_.pairs(unordered),function(o){return o[0]}));
}
如果你不信任你的浏览器来保持键的顺序,我强烈建议你依赖一个键值配对数组的有序数组。
_.sortBy(_.pairs(c),function(o){return o[0]})
这个问题的其他答案是过时的,从未与实现现实相匹配,并且在ES6/ES2015规范发布后正式变得不正确。
请参阅Axel Rauschmayer在《探索ES6》中关于属性迭代顺序的章节:
所有迭代属性键的方法都以相同的顺序执行:首先是数组索引,按数字排序。然后按创建顺序列出所有字符串键(不是索引)。然后是所有符号,按照它们的创建顺序。
是的,JavaScript对象实际上是有序的,它们的键/财产的顺序可以更改。
以下是如何按关键字/财产按字母顺序对对象进行排序:
常量无序={'b':'foo',“c”:“bar”,“a”:“baz”};console.log(JSON.stringify(无序));// → '{“b”:“foo”,“c”:“bar”,“a”:“baz”}'const ordered=Object.keys(无序).sort().reduce((obj,key)=>{obj[key]=无序[key];返回obj;}, {});console.log(JSON.stringify(有序));// → '{“a”:“baz”,“b”:“foo”,“c”:“bar”}'
为了与ES5引擎兼容,请使用var而不是const。
解决方案:
function getSortedObject(object) {
var sortedObject = {};
var keys = Object.keys(object);
keys.sort();
for (var i = 0, size = keys.length; i < size; i++) {
key = keys[i];
value = object[key];
sortedObject[key] = value;
}
return sortedObject;
}
// Test run
getSortedObject({d: 4, a: 1, b: 2, c: 3});
说明:
许多JavaScript运行时将值按添加顺序存储在对象内。
要按键对对象的财产进行排序,可以使用object.keys函数,该函数将返回键数组。然后可以通过array.prototype.sort()方法对键数组进行排序,该方法对数组中的元素进行排序(无需将它们分配给新变量)。
键排序后,您可以开始逐个使用它们来访问旧对象的内容,以填充新对象(现在已排序)。
以下是该过程的示例(您可以在目标浏览器中进行测试):
/***返回对象的副本,该副本按原始对象的键排序。**@param{Object}Object-原始对象。*@返回{Object}按关键字排序的原始对象的副本。*/函数getSortedObject(对象){//将返回带有排序键的新对象var sortedObject={};//从旧/当前对象获取密钥数组var keys=对象.keys(对象);//排序键(在位)keys.sort();//使用排序键将值从旧对象复制到新对象for(var i=0,size=keys.length;i<size;i++){key=键[i];value=对象[key];sortedObject[key]=值;}//返回新对象return sortedObject;}/***试运行*/var unsortedObject={d: 4中,a: 1中,b: 2,c: 3个};var sortedObject=getSortedObject(未排序对象);for(sortedObject中的var键){var text=“Key:”+Key+“,Value:”+sortedObject[Key];var段落=document.createElement('p');paragraph.textContent=text;document.body.appendChild(段落);}
注意:Object.keys是一个ECMAScript 5.1方法,但这里有一个用于旧浏览器的polyfill:
if (!Object.keys) {
Object.keys = function (object) {
var key = [];
var property = undefined;
for (property in object) {
if (Object.prototype.hasOwnProperty.call(object, property)) {
key.push(property);
}
}
return key;
};
}
简单易读的代码段,使用lodash。
只有在调用sortBy时,才需要将键放在引号中。它不必在数据本身的引号中。
_.sortBy(myObj, "key")
另外,要映射的第二个参数是错误的。这应该是一种功能,但使用勇气更容易。
_.map( _.sortBy(myObj, "key") , "value");
也许更优雅的形式:
/***按键对键值对象排序,保持键到数据的相关性。*@param{Object}src键值对象*@return{Object}*/var ksort=函数(src){var keys=对象.keys(src),目标={};keys.sort();key.forEach(功能(键){target[key]=src[key];});回归目标;};//用途console.log(ksort({a: 1中,c: 3中,b: 2个}));
P.S.和ES6+语法相同:
function ksort( src ) {
const keys = Object.keys( src );
keys.sort();
return keys.reduce(( target, key ) => {
target[ key ] = src[ key ];
return target;
}, {});
};
我将一些Java枚举转换为javascript对象。
这些对象为我返回了正确的数组。如果对象键是混合类型(string、int、char),则存在问题。
var助手={isEmpty:函数(obj){回来obj | | obj===null | | obj===未定义| | Array.isArray(obj)&&obj.length===0;},isObject:函数(obj){return(对象类型==“object”);},sortObjectKeys:函数(对象){return Object.keys(对象).sort(函数(a,b){c=a-b;返回c});},containsItem:函数(arr,item){if(arr&&Array.isArray(arr)){return arr.indexOf(项)>-1;}其他{返回arr==项;}},pushArray:函数(arr1,arr2){if(arr1&&arr2&&Array.isArray(arr1)){arr1.push.apply(arr1,Array.isArray(arr2)?arr2:[arr2]);}}};函数TypeHelper(){var_types=参数[0],_defTypeIndex=0,_电流类型,_价值;if(arguments.length==2){_defTypeIndex=参数[1];}对象定义属性(this{关键字:{get:函数(){return _currentType;},集合:函数(val){_currentType.setType(val,true);},可枚举:真},值:{get:函数(){返回类型[_currentType];},集合:函数(val){_value.setType(val,false);},可枚举:真}});this.getAsList=函数(键){var列表=[];Helper.sortObjectKeys(_types).forEach(函数(键、idx、数组){if(键和类型[key]){if(!Helper.isEmpty(keys)&&Helper.containsItem(keys,key)|| Helper.isEmpty(key)){var json={};json.Key=密钥;json.Value=_types[key];Helper.pushArray(列表,json);}}});返回列表;};this.setType=函数(值,isKey){if(!Helper.isEmpty(value)){Object.keys(_types).forEach(函数(key,idx,array){if(Helper.isObject(值)){if(value&&value.Key==Key){_currentType=键;}}else if(isKey){if(value&&value.toString()==key.toString()){_currentType=键;}}否则如果(value&&value.toString()==_types[key]){_currentType=键;}});}其他{this.setDefaultType();}return isKey_类型[_currentType]:_currentType;};this.setTypeByIndex=函数(索引){var keys=Helper.sortObjectKeys(_types);对于(var i=0;i<keys.length;i++){如果(索引==i){_currentType=键[index];打破}}};this.setDefaultType=函数(){this.setTypeByIndex(_defTypeIndex);};this.setDefaultType();}变量类型A={“-1”:“任意”,“2”:“2L”,“100”:“100L”,“200”:“200L”,“1000”:“1000升”};变量类型B={“U”:“任意”,“W”:“1L”,“V”:“2L”,“A”:“100L”,“Z”:“200L”,“K”:“1000L”};console.log('keys of TypeA',Helper.sortObjectKeys(TypeA))//A类钥匙[“-1”、“2”、“100”、“200”、“1000”]console.log('keys of TypeB',Helper.sortObjectKeys(TypeB))//B类键[“U”、“W”、“V”、“A”、“Z”、“K”]var objectTypeA=新TypeHelper(TypeA),objectTypeB=新的TypeHelper(TypeB);console.log('listofobjectA=',objectTypeA.getAsList());console.log('listofobjectB=',objectTypeB.getAsList());
Types:
var TypeA = {
"-1": "Any",
"2": "2L",
"100": "100L",
"200": "200L",
"1000": "1000L"
};
var TypeB = {
"U": "Any",
"W": "1L",
"V": "2L",
"A": "100L",
"Z": "200L",
"K": "1000L"
};
Sorted Keys(output):
Key list of TypeA -> ["-1", "2", "100", "200", "1000"]
Key list of TypeB -> ["U", "W", "V", "A", "Z", "K"]
这是一个老问题,但从Mathias Bynens的回答中得到启示,我制作了一个简短的版本来对当前对象进行排序,而没有太多开销。
Object.keys(unordered).sort().forEach(function(key) {
var value = unordered[key];
delete unordered[key];
unordered[key] = value;
});
代码执行后,“无序”对象本身将按字母顺序对键进行排序。
对Object进行排序的纯JavaScript答案。这是我所知道的唯一能处理负数的答案。此函数用于对数字对象进行排序。
输入obj={1000:{},-1200:{},10000:{},200:}};
function osort(obj) {
var keys = Object.keys(obj);
var len = keys.length;
var rObj = [];
var rK = [];
var t = Object.keys(obj).length;
while(t > rK.length) {
var l = null;
for(var x in keys) {
if(l && parseInt(keys[x]) < parseInt(l)) {
l = keys[x];
k = x;
}
if(!l) { // Find Lowest
var l = keys[x];
var k = x;
}
}
delete keys[k];
rK.push(l);
}
for (var i = 0; i < len; i++) {
k = rK[i];
rObj.push(obj[k]);
}
return rObj;
}
输出将是一个按这些数字排序的对象,新键从0开始。
这里是一个基于lodash的干净版本,可以处理嵌套对象
/**
* Sort of the keys of an object alphabetically
*/
const sortKeys = function(obj) {
if(_.isArray(obj)) {
return obj.map(sortKeys);
}
if(_.isObject(obj)) {
return _.fromPairs(_.keys(obj).sort().map(key => [key, sortKeys(obj[key])]));
}
return obj;
};
如果lodash有一个toObject()方法,它会更干净。。。
只需使用lodash解压缩map并sortBy对的第一个值,然后再次zip,它将返回排序的键。
如果要按值排序,请将对索引更改为1而不是0
var o = { 'b' : 'asdsad', 'c' : 'masdas', 'a' : 'dsfdsfsdf' };
console.log(_(o).toPairs().sortBy(0).fromPairs().value())
@sindresorhus有一个很棒的项目,叫做排序键,非常棒。
您可以在此处查看其源代码:
https://github.com/sindresorhus/sort-keys
或者您可以将其与npm一起使用:
$ npm install --save sort-keys
以下也是他的自述文件中的代码示例
const sortKeys = require('sort-keys');
sortKeys({c: 0, a: 0, b: 0});
//=> {a: 0, b: 0, c: 0}
sortKeys({b: {b: 0, a: 0}, a: 0}, {deep: true});
//=> {a: 0, b: {a: 0, b: 0}}
sortKeys({c: 0, a: 0, b: 0}, {
compare: (a, b) => -a.localeCompare(b)
});
//=> {c: 0, b: 0, a: 0}
只是为了简化它,让它更清晰,马特·鲍尔的答案
//您的对象变量myObj={b:'asdsadfd',c:“masdasaf”,a:'dsfdsfsdf'};//固定代码var键=[];for(myObj中的var k){如果(myObj.hasOwnProperty(k)){按键.按键(k);}}keys.sort();对于(var i=0;i<keys.length;i++){k=键[i];警报(k+':'+myObj[k]);}
function sortObjectKeys(obj){
return Object.keys(obj).sort().reduce((acc,key)=>{
acc[key]=obj[key];
return acc;
},{});
}
sortObjectKeys({
telephone: '069911234124',
name: 'Lola',
access: true,
});
递归排序,用于嵌套对象和数组
function sortObjectKeys(obj){
return Object.keys(obj).sort().reduce((acc,key)=>{
if (Array.isArray(obj[key])){
acc[key]=obj[key].map(sortObjectKeys);
}
if (typeof obj[key] === 'object'){
acc[key]=sortObjectKeys(obj[key]);
}
else{
acc[key]=obj[key];
}
return acc;
},{});
}
// test it
sortObjectKeys({
telephone: '069911234124',
name: 'Lola',
access: true,
cars: [
{name: 'Family', brand: 'Volvo', cc:1600},
{
name: 'City', brand: 'VW', cc:1200,
interior: {
wheel: 'plastic',
radio: 'blaupunkt'
}
},
{
cc:2600, name: 'Killer', brand: 'Plymouth',
interior: {
wheel: 'wooden',
radio: 'earache!'
}
},
]
});
ES6-这是1内衬
var数据={zIndex:99,名称:“Ravan”,年龄:25岁,位置:“架构”,金额:'100k',经理:‘ammu’};console.log(Object.entries(data).sort().reduce((o,[k,v])=>(o[k]=v,o),{}));
在保留引用的同时递归排序键。
function sortKeys(o){
if(o && o.constructor === Array)
o.forEach(i=>sortKeys(i));
else if(o && o.constructor === Object)
Object.entries(o).sort((a,b)=>a[0]>b[0]?1:-1).forEach(e=>{
sortKeys(e[1]);
delete o[e[0]];
o[e[0]] = e[1];
});
}
例子:
let x = {d:3, c:{g:20, a:[3,2,{s:200, a:100}]}, a:1};
let y = x.c;
let z = x.c.a[2];
sortKeys(x);
console.log(x); // {a: 1, c: {a: [3, 2, {a: 1, s: 2}], g: 2}, d: 3}
console.log(y); // {a: [3, 2, {a: 100, s: 200}}, g: 20}
console.log(z); // {a: 100, s: 200}
伙计们,我简直惊呆了!当然,所有的答案都有些陈旧,但没有人提到排序的稳定性!所以请耐心等待,我会尽力回答这个问题,并在这里详细说明。所以我现在要道歉,这将是很多阅读。
由于是2018年,我将只使用ES6,Polyfills都可以在MDN文档中找到,我将在给定部分链接。
问题的答案:
如果你的键只是数字,那么你可以安全地使用Object.keys()和Array.protocol.reduce()来返回排序后的对象:
// Only numbers to show it will be sorted.
const testObj = {
'2000': 'Articel1',
'4000': 'Articel2',
'1000': 'Articel3',
'3000': 'Articel4',
};
// I'll explain what reduces does after the answer.
console.log(Object.keys(testObj).reduce((accumulator, currentValue) => {
accumulator[currentValue] = testObj[currentValue];
return accumulator;
}, {}));
/**
* expected output:
* {
* '1000': 'Articel3',
* '2000': 'Articel1',
* '3000': 'Articel4',
* '4000': 'Articel2'
* }
*/
// if needed here is the one liner:
console.log(Object.keys(testObj).reduce((a, c) => (a[c] = testObj[c], a), {}));
但是,如果您使用字符串,我强烈建议将Array.prototype.sort()链接到所有这些字符串中:
// String example
const testObj = {
'a1d78eg8fdg387fg38': 'Articel1',
'z12989dh89h31d9h39': 'Articel2',
'f1203391dhj32189h2': 'Articel3',
'b10939hd83f9032003': 'Articel4',
};
// Chained sort into all of this.
console.log(Object.keys(testObj).sort().reduce((accumulator, currentValue) => {
accumulator[currentValue] = testObj[currentValue];
return accumulator;
}, {}));
/**
* expected output:
* {
* a1d78eg8fdg387fg38: 'Articel1',
* b10939hd83f9032003: 'Articel4',
* f1203391dhj32189h2: 'Articel3',
* z12989dh89h31d9h39: 'Articel2'
* }
*/
// again the one liner:
console.log(Object.keys(testObj).sort().reduce((a, c) => (a[c] = testObj[c], a), {}));
如果有人想知道reduce的作用:
// Will return Keys of object as an array (sorted if only numbers or single strings like a,b,c).
Object.keys(testObj)
// Chaining reduce to the returned array from Object.keys().
// Array.prototype.reduce() takes one callback
// (and another param look at the last line) and passes 4 arguments to it:
// accumulator, currentValue, currentIndex and array
.reduce((accumulator, currentValue) => {
// setting the accumulator (sorted new object) with the actual property from old (unsorted) object.
accumulator[currentValue] = testObj[currentValue];
// returning the newly sorted object for the next element in array.
return accumulator;
// the empty object {} ist the initial value for Array.prototype.reduce().
}, {});
如果需要,这里是对单线的解释:
Object.keys(testObj).reduce(
// Arrow function as callback parameter.
(a, c) =>
// parenthesis return! so we can safe the return and write only (..., a);
(a[c] = testObj[c], a)
// initial value for reduce.
,{}
);
减少的文件:https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/Reduce为什么在JavaScript返回语句中使用括号:http://jamesknelson.com/javascript-return-parenthesis/
为什么排序有点复杂:
简而言之,Object.keys()将返回一个数组,其顺序与我们使用普通循环得到的顺序相同:
const object1 = {
a: 'somestring',
b: 42,
c: false
};
console.log(Object.keys(object1));
// expected output: Array ["a", "b", "c"]
Object.keys()返回元素为字符串的数组对应于直接在对象上找到的可枚举财产。财产的顺序与循环给出的顺序相同手动覆盖对象的财产。
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/keys
侧记-您也可以在数组上使用Object.keys(),请记住索引将被返回:
// simple array
const arr = ['a', 'b', 'c'];
console.log(Object.keys(arr)); // console: ['0', '1', '2']
但这并不像这些例子所显示的那样简单,现实世界中的对象可能包含数字、字母字符甚至符号(请不要这样做)。
下面是一个示例,所有这些都在一个对象中:
// This is just to show what happens, please don't use symbols in keys.
const testObj = {
'1asc': '4444',
1000: 'a',
b: '1231',
'#01010101010': 'asd',
2: 'c'
};
console.log(Object.keys(testObj));
// output: [ '2', '1000', '1asc', 'b', '#01010101010' ]
现在,如果我们对上面的数组使用Array.protocol.sort(),输出将发生变化:
console.log(Object.keys(testObj).sort());
// output: [ '#01010101010', '1000', '1asc', '2', 'b' ]
以下是文档中的引用:
sort()方法就地对数组的元素进行排序并返回阵列。排序不一定稳定。默认排序顺序是根据字符串Unicode代码点。排序的时间和空间复杂性无法保证取决于实现。
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/sort
您必须确保其中一个为您返回所需的输出。在现实生活中,如果你同时使用不同的信息输入(如API和数据库),人们往往会把事情搞混。
那有什么大不了的?
每个程序员都应该理解以下两篇文章:
就地算法:
在计算机科学中,就地算法是一种不使用辅助数据结构转换输入的算法。但是,允许为辅助变量提供少量的额外存储空间。当算法执行时,输入通常被输出覆盖。就地算法仅通过替换或交换元素来更新输入序列。不到位的算法有时被称为不到位或不到位。
所以基本上我们的旧阵列将被覆盖!如果出于其他原因想保留旧阵列,这一点很重要。所以请记住这一点。
排序算法
稳定排序算法以与它们出现在输入中。对某些类型的数据进行排序时,仅部分在确定排序顺序时检查数据的排序。例如在右边的卡片排序示例中,卡片正在排序而他们的诉讼却被忽视了。这允许多个不同的正确排序版本的可能性原始列表。稳定的排序算法选择其中之一,根据以下规则:如果两项比较相等,例如两张5卡,则它们的相对顺序将被保留,这样如果输入中的一个在另一个之前,它也会在前面另一个在输出中。
扑克牌中的一个稳定类型的例子。卡片分类时按稳定排序排序,两个5s必须保持相同的顺序在它们最初所在的排序输出中用非稳定排序,5s可能以相反的顺序结束在排序的输出中。
这表明排序是正确的,但它发生了变化。所以在现实世界中,即使排序是正确的,我们也必须确保得到我们期望的结果!这是非常重要的,请记住这一点。有关更多JavaScript示例,请查看Array.prototype.sort()-docs:https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/sort
不确定这是否能回答问题,但这正是我需要的。
Maps.iterate.sorted = function (o, callback) {
var keys = Object.keys(o), sorted = keys.sort(), k;
if ( callback ) {
var i = -1;
while( ++i < sorted.length ) {
callback(k = sorted[i], o[k] );
}
}
return sorted;
}
调用为:
Maps.iterate.sorted({c:1, b:2, a:100}, function(k, v) { ... } )
现在是2019年,我们有一个2019年的方法来解决这个问题:)
Object.fromEntries(Object.entries({b: 3, a:8, c:1}).sort())
Object.keys(unordered).sort().reduce(
(acc,curr) => ({...acc, [curr]:unordered[curr]})
, {}
)
一行:
Object.entries(unordered)
.sort(([keyA], [keyB]) => keyA > keyB)
.reduce((obj, [key,value]) => Object.assign(obj, {[key]: value}), {})
这是一个轻量级的解决方案,可以满足JSON排序所需的一切。
function sortObj(obj) {
if (typeof obj !== "object" || obj === null)
return obj;
if (Array.isArray(obj))
return obj.map((e) => sortObj(e)).sort();
return Object.keys(obj).sort().reduce((sorted, k) => {
sorted[k] = sortObj(obj[k]);
return sorted;
}, {});
}
最好的方法是
const object = Object.keys(o).sort().reduce((r, k) => (r[k] = o[k], r), {})
//else if its in reverse just do
const object = Object.keys(0).reverse ()
您可以首先将几乎类似数组的对象转换为实际数组,然后使用.reverse():
Object.assign([], {1:'banana', 2:'apple',
3:'orange'}).reverse();
// [ "orange", "apple", "banana", <1 empty slot> ]
结尾处的空槽if cause,因为第一个索引是1而不是0。可以使用.length--或.pop()删除空槽。
或者,如果您想借用.reverse并在同一个对象上调用它,它必须是一个完全类似数组的对象。也就是说,它需要长度属性:
Array.prototype.reverse.call({1:'banana', 2:'apple',
3:'orange', length:4});
// {0:"orange", 1:"apple", 3:"banana", length:4}
注意,它将返回同一个完全类似数组的对象对象,因此它不是一个真正的数组。然后可以使用delete删除长度属性。
事实上,我非常惊讶的是,给出了30多个答案,但没有一个给出了这个问题的完整深度解决方案。有些解决方案很浅,而另一些解决方案很深,但有缺陷(如果未定义,则会崩溃,函数或符号将在json中)。
以下是完整的解决方案:
function sortObject(unordered, sortArrays = false) {
if (!unordered || typeof unordered !== 'object') {
return unordered;
}
if (Array.isArray(unordered)) {
const newArr = unordered.map((item) => sortObject(item, sortArrays));
if (sortArrays) {
newArr.sort();
}
return newArr;
}
const ordered = {};
Object.keys(unordered)
.sort()
.forEach((key) => {
ordered[key] = sortObject(unordered[key], sortArrays);
});
return ordered;
}
const json = {
b: 5,
a: [2, 1],
d: {
b: undefined,
a: null,
c: false,
d: true,
g: '1',
f: [],
h: {},
i: 1n,
j: () => {},
k: Symbol('a')
},
c: [
{
b: 1,
a: 1
}
]
};
console.log(sortObject(json, true));
这里有一个单行解决方案(不是最有效的,但当涉及到像您的示例中那样的瘦对象时,我宁愿使用本机JS函数,也不要使用草率的循环)
const无序={“b”:“asdsad”,“c”:“masdas”,“a”:“dsfdsfsdf”}const ordered=Object.fromEntries(Object.entries(无序).sort())console.log(已订购);//a->b->c
// if keys are char/string
const sortObject = (obj) => Object.fromEntries(Object.entries(obj).sort( ));
let obj = { c: 3, a: 1 };
obj = sortObject(obj)
// if keys are numbers
const sortObject = (obj) => Object.fromEntries(Object.entries(obj).sort( (a,b)=>a-b ));
let obj = { 3: 'c', 1: 'a' };
obj = sortObject(obj)
我喜欢上面的这个,只是它不起作用:
/**
* Return an Object sorted by it's Key
*/
var sortObjectByKey = function(obj){
var keys = [];
var sorted_obj = {};
for(var key in obj){
if(obj.hasOwnProperty(key)){
keys.push(key);
}
}
// sort keys
keys.sort();
// create new array based on Sorted Keys
jQuery.each(keys, function(i, key){
sorted_obj[key] = obj[key];
});
return sorted_obj;
};
看起来像sorted_obj,没有秩序的保证,因为那张地图似乎更适合,我最终改变了地图的对象,类似这样:
/**
* Return an Object sorted by it's Key
*/
var sortObjectByKey = function(obj){
var keys = [];
let sorted_map = new Map();
for(var key in obj){
if(obj.hasOwnProperty(key)){
keys.push(key);
}
}
// sort keys
keys.sort();
// create new map based on Sorted Keys
keys.forEach(key => {
sorted_map.set(key, obj[key]);
});
return sorted_map;
};
const sortObjectByKeys=(对象,asc=true)=>object.fromEntries(Object.entries(Object).sort(([k1],[k2])=>k1<k2^!阿斯克-1 : 1),)常量对象={b:“asdsad”,c:“masdas”,a:“dsfdsfsdf”}const orderedObject=sortObjectByKeys(对象)console.log(orderedObject)
截至2023年1月
变量obj={'b':'Val',“a”:“Val”,'c':'bVal'}console.log(JSON.stringify(obj))obj=Object.fromEntries(Object.entries(obj).sort())console.log(JSON.stringify(obj));