我有以下陣列:
const getUsers = () => {
return new Promise((resolve, reject) => {
setTimeout(() => {
resolve([
{ id: 1, name: 'User 1', active: 'active' },
{ id: 2, name: 'User 2', active: 'active' },
{ id: 3, name: 'User 3', active: 'inactive' },
{ id: 4, name: 'User 4', active: 'active' }
]);
}, 1000);
});
}
const getCompanies = () => {
return new Promise((resolve, reject) => {
setTimeout(() => {
resolve([
{ id: 1, name: 'Company 1', employees: [1, 3], active: 'inactive' },
{ id: 2, name: 'Company 2', employees: [4], active: 'active' },
{ id: 3, name: 'Company 3', employees: [2], active: 'active' }
]);
}, 3000);
});
}
我想要做的是創建另一個公司陣列,但它是匹配的用戶陣列。例如:
{
id: 1,
name: 'Company 1'
employes: [
{ id: 1, name: 'User 1', active: 'active' },
{ id: 3, name: 'User 3', active: 'inactive' }
],
active: 'inactive'
},
{ Company 2... },
{ Comapny 3... }
現在這就是我正在嘗試的:
const getCompaniesWithUsers = async () => {
let companies = await getCompanies();
let users = await getUsers();
let result = await users.filter(x => x.id === companies.map(a => a.id);
}
但根本不起作用,我有一些問題:
- 我應該如何處理兩個 get 函式的 Promise 和 Timeout?因為如果我不使用 async/await 我會得到空的常量。
- 解決我的問題的最佳方式/功能是什么?我認為我需要過濾器、映射和查找功能的組合,但我仍在學習 JS,所以我正在閱讀一些檔案并嘗試解決我的問題。
uj5u.com熱心網友回復:
getUsers您正在正確處理呼叫getCompanies。您需要兩者的資料來建立您的公司及其員工名單。
我建議的唯一修改是使用Promise.all(),以便您并行運行提取。在此代碼段中不會有什么不同,但如果您的方法呼叫某個服務,那么這種方法允許您同時啟動這些請求,而不是等待第一個請求完成后再啟動第二個請求。
你不需要filter任何東西,但Array#find很方便。像您建議的那樣使用Array#map從員工 ID 陣列中創建一個新的員工物件陣列。傳遞給的函式map將通過陣列find中的 id 來處理員工。users
const getUsers = () => {
return new Promise((resolve, reject) => {
setTimeout(() => {
resolve([
{ id: 1, name: 'User 1', active: 'active' },
{ id: 2, name: 'User 2', active: 'active' },
{ id: 3, name: 'User 3', active: 'inactive' },
{ id: 4, name: 'User 4', active: 'active' }
]);
}, 1000);
});
}
const getCompanies = () => {
return new Promise((resolve, reject) => {
setTimeout(() => {
resolve([
{ id: 1, name: 'Company 1', employees: [1, 3], active: 'inactive' },
{ id: 2, name: 'Company 2', employees: [4], active: 'active' },
{ id: 3, name: 'Company 3', employees: [2], active: 'active' }
]);
}, 3000);
});
}
const getCompaniesWithUsers = async () => {
return Promise.all([getCompanies(), getUsers()]).then(([companies, users]) => {
const filledCompanies = companies.map(c => {
return {
...c,
employees: c.employees.map(e => users.find(u => u.id === e))
};
});
return filledCompanies;
});
}
getCompaniesWithUsers().then(c => console.log(c));
如果您正在學習 Javascript,我的回答中有一些概念可以使用一些解釋:
解構
無需將運算式的結果分配給單個變數然后訪問變數上的欄位,您可以將運算式的結果分配給物件或陣列并直接訪問欄位。它比這更復雜,但這就是要點。這是解構分配的檔案。
以下兩個片段的功能(大致)相同,但第一個避免了第二個所需的額外分配。如果您不經常使用它,它可能會或可能不值得它看起來多么令人困惑。
Promise.all([getCompanies(), getUsers()]).then(([companies, users]) => // ...
Promise.all([getCompanies(), getUsers()]).then(values => {
const companies = values[0];
const users = values[1];
// ...
傳播語法
另一個速記技巧,擴展語法允許您將可迭代物件擴展為物件或陣列。
以下兩個片段的功能(大致)相同,但第一個再次避免了第二個所需的額外代碼。
const a = { id: 1, name: 'Foo' };
const b = { ...a, hobby: 'Coding' };
const a = { id: 1, name: 'Foo' };
const b = { id: a.id, name: a.name, hobby: 'Coding' };
物件字面量
如果您查看這部分代碼:
const filledCompanies = companies.map(c => {
return {
...c,
employees: c.employees.map(e => users.find(u => u.id === e))
};
});
回傳的匿名物件是使用物件文字方法創建的,其中一對花括號圍繞一系列key: value對。
檔案說如果有兩個實體 a key,第二個會覆寫第一個。我在這里使用它來company在映射時覆寫物件上的一個欄位。
通過將物件傳播company到回傳的匿名物件中,匿名物件employees從物件中獲取欄位company。也就是說,它獲取用戶識別符號陣列。employees然后,我使用識別符號陣列映射到用戶物件陣列的結果顯式定義另一個欄位。因為我的定義在后面,所以它會覆寫用戶識別符號陣列。
您必須注意使用它的環境。檔案:
在 ECMAScript 5 嚴格模式代碼中,重復的屬性名稱被認為是
SyntaxError. 隨著計算屬性名稱的引入使得在運行時復制成為可能,ECMAScript 2015 移除了這個限制。
如果您發現無法使用它,以下方法也可以使用:
const filledCompanies = companies.map(c => {
const company = c;
company.employees = c.employees.map(e => users.find(u => u.id === e));
return company;
});
uj5u.com熱心網友回復:
filter()不是異步的,你不需要等待它。您之前的 await 回傳的陣列,您可以正常處理它們。
你不需要filter()。employees您在屬性中有一個用戶 ID 陣列,只需對其進行映射以獲取users. 用于按 IDfind()搜索users陣列。
const getCompaniesWithUsers = async() => {
let companies = await getCompanies();
let users = await getUsers();
companies.forEach(c => c.employees = c.employees.map(eid => users.find(u => u.id == eid)));
return companies;
}
要使用它,您可以使用
companies_with_users = await getCompaniesWithUsers();
如果你在一個異步函式中,或者
getCompaniesWithUsers().then(companies_with_users => {
...
});
如果不。
轉載請註明出處,本文鏈接:https://www.uj5u.com/shujuku/467424.html
標籤:javascript 数组
上一篇:將串列中的值剪切到逗號
