admin管理员组文章数量:1128021
I have an extremely large JSON object structured like this:
{A : 1, B : 2, C : 3, D : 4}
I need a function that can swap the values with keys in my object and I don't know how to do it. I would need an output like this:
{1 : A, 2 : B, 3 : C, 4 : D}
Is there any way that I can do this would manually created a new object where everything is swapped?
Thanks
I have an extremely large JSON object structured like this:
{A : 1, B : 2, C : 3, D : 4}
I need a function that can swap the values with keys in my object and I don't know how to do it. I would need an output like this:
{1 : A, 2 : B, 3 : C, 4 : D}
Is there any way that I can do this would manually created a new object where everything is swapped?
Thanks
25 Answers
Reset to default 189function swap(json){
var ret = {};
for(var key in json){
ret[json[key]] = key;
}
return ret;
}
Example here FIDDLE don't forget to turn on your console to see the results.
ES6 versions:
static objectFlip(obj) {
const ret = {};
Object.keys(obj).forEach(key => {
ret[obj[key]] = key;
});
return ret;
}
Or using Array.reduce() & Object.keys()
static objectFlip(obj) {
return Object.keys(obj).reduce((ret, key) => {
ret[obj[key]] = key;
return ret;
}, {});
}
Or using Array.reduce() & Object.entries()
static objectFlip(obj) {
return Object.entries(obj).reduce((ret, entry) => {
const [ key, value ] = entry;
ret[ value ] = key;
return ret;
}, {});
}
Now that we have Object.fromEntries:
const f = obj => Object.fromEntries(Object.entries(obj).map(a => a.reverse()))
console.log(
f({A : 'a', B : 'b', C : 'c'})
) // => {a : 'A', b : 'B', c : 'C'}
or:
const f = obj => Object.fromEntries(Object.entries(obj).map(([k, v]) => [v, k]))
console.log(
f({A : 'a', B : 'b', C : 'c'})
) // => {a : 'A', b : 'B', c : 'C'}
(Updated to remove superfluous parentheses - thanks @devin-g-rhode)
you can use lodash function _.invert it also can use multivlaue
var object = { 'a': 1, 'b': 2, 'c': 1 };
_.invert(object);
// => { '1': 'c', '2': 'b' }
// with `multiValue`
_.invert(object, true);
// => { '1': ['a', 'c'], '2': ['b'] }
Using ES6:
const obj = { a: "aaa", b: "bbb", c: "ccc", d: "ddd" };
Object.assign({}, ...Object.entries(obj).map(([a,b]) => ({ [b]: a })))
Get the keys of the object, and then use the Array's reduce function to go through each key and set the value as the key, and the key as the value.
const data = {
A: 1,
B: 2,
C: 3,
D: 4
}
const newData = Object.keys(data).reduce(function(obj, key) {
obj[data[key]] = key;
return obj;
}, {});
console.log(newData);
In ES6/ES2015 you can combine use of Object.keys and reduce with the new Object.assign function, an arrow function, and a computed property name for a pretty straightforward single statement solution.
const foo = { a: 1, b: 2, c: 3 };
const bar = Object.keys(foo)
.reduce((obj, key) => Object.assign({}, obj, { [foo[key]]: key }), {});
If you're transpiling using the object spread operator (stage 3 as of writing this) that will simplify things a bit further.
const foo = { a: 1, b: 2, c: 3 };
const bar = Object.keys(foo)
.reduce((obj, key) => ({ ...obj, [foo[key]]: key }), {});
Finally, if you have Object.entries available (stage 4 as of writing), you can clean up the logic a touch more (IMO).
const foo = { a: 1, b: 2, c: 3 };
const bar = Object.entries(foo)
.reduce((obj, [key, value]) => ({ ...obj, [value]: key }), {});
2021's answer
The concise way by using ES6 syntax like this.
const obj = {A : 1, B : 2, C : 3, D : 4}
console.log(
Object.entries(obj).reduce((acc, [key, value]) => (acc[value] = key, acc), {})
);
Explain:
(acc[value] = key, acc)
Using Comma operator (,) syntax.
The comma operator (,)
evaluates each of its operands (from left to right) and returns the value of the last operand.
As a complement of @joslarson and @jPO answers:
Without ES6 needed, you can use Object.keys
Array.reduce
and the Comma Operator:
Object.keys(foo).reduce((obj, key) => (obj[foo[key]] = key, obj), {});
Some may find it ugly, but it's "kinda" quicker as the reduce
doesn't spread all the properties of the obj
on each loop.
Modern JS solution:
const swapKeyValue = (object) =>
Object.entries(object).reduce((swapped, [key, value]) => (
{ ...swapped, [value]: key }
), {});
Typescript:
type ValidKey = number | string;
const swapKeyValue = <K extends ValidKey, V extends ValidKey>(
object: Record<K, V>
): Record<V, K> =>
Object.entries(object)
.reduce((swapped, [key, value]) => (
{ ...swapped, [value as ValidKey]: key }
), {} as Record<V, K>);
Using Ramda:
const swapKeysWithValues =
R.pipe(
R.keys,
R.reduce((obj, k) => R.assoc(source[k], k, obj), {})
);
const result = swapKeysWithValues(source);
Try
let swap = (o,r={})=> Object.keys(o).map(k=> r[o[k]]=k) && r;
let obj = {A : 1, B : 2, C : 3, D : 4};
let swap = (o,r={})=> Object.keys(o).map(k=> r[o[k]]=k) && r;
console.log(swap(obj));
With pure Ramda in a pure and point-free style:
const swapKeysAndValues = R.pipe(
R.toPairs,
R.map(R.reverse),
R.fromPairs,
);
Or, with a little more convoluted ES6 version, still pure functional:
const swapKeysAndValues2 = obj => Object
.entries(obj)
.reduce((newObj, [key, value]) => ({...newObj, [value]: key}), {})
Shortest one I came up with using ES6..
const original = {
first: 1,
second: 2,
third: 3,
fourth: 4,
};
const modified = Object
.entries(original)
.reduce((all, [key, value]) => ({ ...all, [value]: key }), {});
console.log('modified result:', modified);
var data = {A : 1, B : 2, C : 3, D : 4}
var newData = {};
Object.keys(data).forEach(function(key){newData[data[key]]=key});
console.log(newData);
Here is a pure functional implementation of flipping keys
and values
in ES6:
TypeScript
const flipKeyValues = (originalObj: {[key: string]: string}): {[key: string]: string} => {
if(typeof originalObj === "object" && originalObj !== null ) {
return Object
.entries(originalObj)
.reduce((
acc: {[key: string]: string},
[key, value]: [string, string],
) => {
acc[value] = key
return acc;
}, {})
} else {
return {};
}
}
JavaScript
const flipKeyValues = (originalObj) => {
if(typeof originalObj === "object" && originalObj !== null ) {
return Object
.entries(originalObj)
.reduce((acc, [key, value]) => {
acc[value] = key
return acc;
}, {})
} else {
return {};
}
}
const obj = {foo: 'bar'}
console.log("ORIGINAL: ", obj)
console.log("FLIPPED: ", flipKeyValues(obj))
function swapKV(obj) {
const entrySet = Object.entries(obj);
const reversed = entrySet.map(([k, v])=>[v, k]);
const result = Object.fromEntries(reversed);
return result;
}
This can make your object, {A : 1, B : 2, C : 3, D : 4}
, array-like, so you can have
const o = {A : 1, B : 2, C : 3, D : 4}
const arrayLike = swapKV(o);
arrayLike.length = 5;
const array = Array.from(arrayLike);
array.shift(); // undefined
array; // ["A", "B", "C", "D"]
Here is an option that will swap keys with values but not lose duplicates, if your object is : { a: 1, b: 2, c: 2}, it will always return an array in the output :
function swapMap(map) {
const invertedMap = {};
for (const key in map) {
const value = map[key];
invertedMap[value] = invertedMap[value] || [];
invertedMap[value].push(key);
}
return invertedMap;
}
swapMap({a: "1", b: "2", c: "2"})
// Returns => {"1": ["a"], "2":["b", "c"]}
A simple TypeScript variant:
const reverseMap = (map: { [key: string]: string }) => {
return Object.keys(map).reduce((prev, key) => {
const value = map[key];
return { ...prev, [value]: [...(prev.value || []), key] };
}, {} as { [key: string]: [string] })
}
Usage:
const map = { "a":"1", "b":"2", "c":"2" };
const reversedMap = reverseMap(map);
console.log(reversedMap);
Prints:
{ "1":["a"], "2":["b", "c"] }
Rewriting answer of @Vaidd4, but using Object.assign
(instead of comma operator):
/**
* Swap object keys and values
* @param {Object<*>} obj
* @returns {Object<string>}
*/
function swapObject(obj) {
return Object.keys(obj).reduce((r, key) => (Object.assign(r, {
[obj[key]]: key,
})), {});
}
Or, shorter:
Object.keys(obj).reduce((r, key) => (Object.assign(r, {[obj[key]]: key})), {});
function myFunction(obj) {
return Object.keys(obj).reduce((acc, cur) => {
return { ...acc, [obj[cur]]: cur };
}, {});
}
This is the solution that I'm using:
function objSwap(obj, tl = false) {
return Object.entries(obj).reduce((a, [k, v]) => (a[v = tl ? v.toLowerCase() : v] = k = tl ? k.toLowerCase() : k, a), {});
}
As a bonus: if you need to swap then check some values I added the possibility to lowercase keys and values. Simply you've to set tl = true
, else if you don't need it ...
function objSwap(obj) {
return Object.entries(obj).reduce((a, [k, v]) => (a[v] = k, a), {});
}
Using a for...of
loop:
let obj = {A : 1, B : 2, C : 3, D : 4}
for (let [key, value] of Object.entries(obj)){
obj[value] = key
delete obj[key]
}
console.log(obj) // {1: 'A', 2: 'B', 3: 'C', 4: 'D'}
ONE OF THE ES6 WAYS IS HERE
const invertObject = (object) =>Object.entries(object).reduce((result, value) => ({...result, [value[1]]: value[0] }), {});
let obj = invertObject({A : 1, B : 2, C : 3, D : 4});
Here's a type-safe way using TypeScript that has not been suggested before. This solution takes two generics that means the return type will be typed as expected. It's faster than doing methods with .reduce
or Object.entries
.
// Easier way to type `symbol | number | string` (the only valid keys of an object)
export type AnyKey = keyof any;
export function mirror<K extends AnyKey, V extends AnyKey>(
object: Record<K, V>,
) {
const ret: Partial<Record<V, K>> = {};
for (const key in object) {
ret[object[key]] = key;
}
return ret as Record<V, K>;
}
Usage:
const obj = mirror({
a: 'b',
c: 'd',
});
// {b: 'a', d: 'c'}
obj;
I believe it's better to do this task by using an npm module, like invert-kv
.
invert-kv: Invert the key/value of an object. Example: {foo: 'bar'} → {bar: 'foo'}
https://www.npmjs.com/package/invert-kv
const invertKv = require('invert-kv');
invertKv({foo: 'bar', unicorn: 'rainbow'});
//=> {bar: 'foo', rainbow: 'unicorn'}
本文标签: javascriptSwap key with value in objectStack Overflow
版权声明:本文标题:javascript - Swap key with value in object - Stack Overflow 内容由网友自发贡献,该文观点仅代表作者本人, 转载请联系作者并注明出处:http://www.betaflare.com/web/1736706336a1948697.html, 本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,一经查实,本站将立刻删除。
function swap(obj) {return new Map(Object.entries(x).map([k, v] => [v, k]))}
– broofa Commented Feb 1, 2019 at 21:44const swap = o => Object.entries(o).reduce((r, [k, v]) => (r[v]=k, r), {});
Similar approach can be used for arrays where values are positive integers/indices. – mpapec Commented Oct 21, 2020 at 8:21