[英]How to convert a single dimensional object to a multi-dimensional object in JavaScript?
這里我做了一個代碼,將多維的 object 轉換為一維的 object ->
const magic = (obj, parent)=>{
for(let key in obj){
if(typeof obj[key] === 'object')
{
magic(obj[key], parent+"-"+key);
}
else{
ans[parent + "-" + key] = obj[key];
}
}
}
const obj = {
id: 101,
email: 'jack@dev.com',
personalInfo: {
name: 'Jack',
address: {
line1: 'westwish st',
line2: 'washmasher',
city: 'wallas',
state: 'WX'
}
}
}
magic(obj, "obj");
我試圖再次將這個一維 object 變成一個多維 object 但遇到了很多錯誤。 請幫助我編寫 function 以將此一維 object 轉換為多維 object。
轉換后的一維 object 示例:
{
obj-id: 101 ,
obj-email: "jack@dev.com" ,
obj-personalInfo-name: "Jack" ,
obj-personalInfo-address-line1: "westwish st" ,
obj-personalInfo-address-line2: "washmasher" ,
obj-personalInfo-address-city: "wallas" ,
obj-personalInfo-address-state: "WX"
}
您可以通過首先創建結果 object 來迭代地執行此操作,該結果將包含來自您輸入 object 的鍵。 對於每個鍵,您可以按-
拆分,以獲取數組中 object 的各個鍵。 您還可以從鍵數組中彈出最后一個鍵,以便在達到最終 object 后將其設置為一個值。 對於每個密鑰,您可以檢查它是否存在於當前 object 中,如果存在,則更新當前指針以指向該 object,否則,您可以為給定密鑰創建一個新的空 object。 到達最后一個 object 后,您可以將之前從陣列中彈出的密鑰設置到當前的 object 上,如下所示:
const reverseMagic = (obj)=>{ const res = {}; for(const path in obj) { const keys = path.split('-'); const last = keys.pop(); // Walk down the properties, create them if they don't exist let curr = res; for(const key of keys) { curr[key] = curr[key] || {}; curr = curr[key]; } curr[last] = obj[path]; } return res; } const obj = { "obj-id": 101, "obj-email": "jack@dev.com", "obj-personalInfo-name": "Jack", "obj-personalInfo-address-line1": "westwish st", "obj-personalInfo-address-line2": "washmasher", "obj-personalInfo-address-city": "wallas", "obj-personalInfo-address-state": "WX" }; console.log(reverseMagic(obj));
我們可以在 function 上構建它,它向 object 添加諸如['personalInfo', 'address', 'city']
類的路徑和關聯值,如下所示:
const addPath = ([p, ...ps], val, obj) =>
ps .length == 0
? {...obj, [p]: val}
: {...obj, [p]: addPath (ps, val, obj[p] || {})}
那么我們的逆魔function就很簡單了:
const cigam = (obj) => // "magic" backwards
Object .entries (obj)
.reduce ((a, [k, v]) => addPath (k .split ('-'), v, a), {})
但是,我也認為您的magic
function 可以清理一下,特別是因為它正在更改其ans
之外的變量。 我經常寫一些版本的pathEntries
可以將你的原件轉換成類似的東西
[
['id', 101] ,
['email', 'jack@dev.com'],
['personalInfo-name', 'Jack'],
['personalInfo-address-line1', 'westwish st'],
['personalInfo-address-line2', 'washmasher'],
['personalInfo-address-city', 'wallas'],
['personalInfo-address-state', 'WX']
]
有了它,我們就可以像寫magic
一樣簡單了
const magic = (obj) =>
Object .fromEntries (pathEntries (obj))
這不包括您的parent
屬性,這對我來說似乎是多余的,但如果您想要它,我們只需添加一點:
const magic = (obj, parent) =>
Object .fromEntries (pathEntries (obj) .map (([k, v]) => [`${parent}-${k}`, v]))
把這一切放在一起,我們可以這樣做:
const pathEntries = (obj) => Object (obj) === obj? Object.entries (obj).flatMap ( ([k, x]) => pathEntries (x).map (([p, v]) => [k + (p? '-': '') + p, v]) ): [['', obj]] const magic = (obj) => Object.fromEntries (pathEntries (obj)) const addPath = ([p, ...ps], val, obj) => ps.length == 0? {...obj, [p]: val}: {...obj, [p]: addPath (ps, val, obj[p] || {})} const cigam = (obj) => // "magic" backwards Object.entries (obj).reduce ((a, [k, v]) => addPath (k.split ('-'), v, a), {}) const obj = {id: 101, email: "jack@dev.com", personalInfo: {name: "Jack", address: {line1: "westwish st", line2: "washmasher", city: "wallas", state: "WX"}}} const enchanted = magic (obj) console.log (enchanted) const unenchanted = cigam (enchanted) console.log (unenchanted)
.as-console-wrapper {max-height: 100%;important: top: 0}
如果你確實想要那個parent
屬性,它不會有太大變化:
const pathEntries = (obj) => Object (obj) === obj? Object.entries (obj).flatMap ( ([k, x]) => pathEntries (x).map (([p, v]) => [k + (p? '-': '') + p, v]) ): [['', obj]] const magic = (obj, name) => Object.fromEntries (pathEntries (obj).map (([k, v]) => [`${name}-${k}`, v])) const addPath = ([p, ...ps], val, obj) => ps.length == 0? {...obj, [p]: val}: {...obj, [p]: addPath (ps, val, obj[p] || {})} const cigam = (obj) => // "magic" backwards Object.entries (obj).reduce ((a, [k, v]) => addPath (k.split ('-'), v, a), {}) const obj = {id: 101, email: "jack@dev.com", personalInfo: {name: "Jack", address: {line1: "westwish st", line2: "washmasher", city: "wallas", state: "WX"}}} const enchanted = magic (obj, 'obj') console.log (enchanted) const unenchanted = cigam (enchanted) ['obj'] console.log (unenchanted)
在這里,我能夠使用遞歸做你需要的事情:
// Demo object
const x = {
obj1: "Hello",
obj2: {
obj3: "hi",
obj4: {
obj5: "greetings",
obj6: "goodbye"
}
}
}
function flatObj(obj){
const flattenObj = {}; // New one dimensional object
// Loop over keys
for (const key in obj) {
if (typeof obj[key] !== "object") {
// If not an object, append it to flattened object
flattenObj[key] = obj[key];
} else {
// If it is an object, flatten the object then append each key
const temp = flatObj(obj[key]);
for(const tempKey in temp){
flattenObj[`${key}-${tempKey}`] = temp[tempKey];
}
}
}
// Return one dimension object
return flattenObj;
}
flatObj(x);
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.