如果类别名称已经在映射函数中呈现,如何显示一次



基本上,我有一系列药物类别。我也有单独的药物类别。

现在,我的代码基本上映射了类别数组中的所有类别,如果药物的类别与类别匹配,它就会将其放在下面

然而,我只想在下拉列表中呈现一个类别,如果drug.class与之匹配。

tldr:drug.class与类别不匹配?然后不要在下拉列表中显示类别。drug.class与类别匹配?呈现类别并将药物放在该类别下,但是,不要对每种药物重复该类别。

基本上,只有当drug.class与category.name匹配时,才会呈现这种效果,所以我没有下面没有药物的空类别。

<ListSubheader key={category.id}>{category.name}</ListSubheader>

我希望我已经尽我所能解释了这一点,这是我的代码:

{categories.map(category => 
(<span>
<ListSubheader key={category.id}>{category.name}</ListSubheader>
{drugs.map(drug => drug.class.toLowerCase()===category.name.toLowerCase() ? 
<>
{ patient.age <= 12 && drug.suggestedDosePediatric != "Restricted" &&
<MenuItem key={drug._id} onClick={()=>handleClick(drug)} value={drug.value}>{drug.name}</MenuItem>
}
{ patient.age > 12 &&
<MenuItem key={drug._id} onClick={()=>handleClick(drug)} value={drug.value}>{drug.name}</MenuItem>
}
</>
: null)}
</span>)
)}

您可以按类别对药物进行分组。

// assuming the following helper
function groupBy(iterable, keyFn) {
const groups = new Map();
for (const item of iterable) {
const key = keyFn(item);
if (!groups.has(key)) groups.set(key, []);
groups.get(key).push(item);
}
return groups;
}

有了上面的助手(或库中类似的东西(,我们可以对药物进行分组,然后对它们进行迭代。

if (patient.age <= 12) {
drugs = drugs.filter(drug => drug.suggestedDosePediatric != "Restricted");
}
const drugsByCategoryName = groupBy(drugs, drug => drug.class.toLowerCase());
// ...
{Array.from(drugsByCategoryName, ([categoryName, drugs]) => (
<span>
<ListSubheader>{categoryName}</ListSubheader>
{drugs.map((drug) => (
<MenuItem key={drug._id} onClick={()=>handleClick(drug)} value={drug.value}>
{drug.name}
</MenuItem>
))}
</span>
))}

以上内容基本上回答了您的问题。尽管您可能已经注意到该类别目前只是一个名称(缺少key={category.id}(。为了访问一个类别的所有属性,最好先为类别创建一个查找对象,因为你必须找到属于每种药物的类别。

const categoriesByName = new Map(categories.map((category) => (
[category.name.toLowerCase(), category]
)));

然后,不再按类别名称进行分组,而是按类别对象对药物进行分组。

const drugsByCategory = groupBy(drugs, (drug) => (
categoriesByName.get(drug.class.toLowerCase()))
));

drugsByCategory的这个新定义是按category对象分组的,而不仅仅是名称。这允许您在迭代时访问类别属性。

{Array.from(drugsByCategoryName, ([category, drugs]) => (
<span>
<ListSubheader key={category.id}>{category.name}</ListSubheader>
{/* ... */}
</span>
))}

;漏洞";在可能导致异常的上述代码中。如果drugs的列表中包含一个不在categories中的drug.class,该怎么办?这样的场景可能不存在,在这种情况下你不必担心。如果这种场景确实存在,上面的代码已经很好地处理了它。categoriesByName.get(drug.class.toLowerCase()))将返回undefined,这意味着所有不存在drug.class的药物都列在drugsByCategory映射中的undefined键下。

这允许不同的解决方案。您可以通过从集合中删除drug.class组来忽略所有不存在的药物。

drugsByCategory.delete(undefined);

另一种选择是添加一个";其他";类别。

const others = drugsByCategory.get(undefined);
drugsByCategory.delete(undefined);
// ...
{Array.from(drugsByCategory, (category, drugs) => (
<span>
<ListSubheader key={category.id}>{category.name}</ListSubheader>
{/* ... */}
</span>
))}
{others && (
<span>
<ListSubheader key="others">Others</ListSubheader>
{/* ... */}
</span>
)}

drugs.filter(drug => drug.class.toLowerCase() === category.name.toLowerCase()将只为您提供所需药物的数组。然后你可以绘制地图。它们可以链接在一起,就像这样:

{categories.map(category => 
(<span>
<ListSubheader key={category.id}>{category.name}</ListSubheader>
{drugs.filter(drug => drug.class.toLowerCase() === category.name.toLowerCase()).map(drug => drug.class.toLowerCase()===category.name.toLowerCase() ? 
<>
{ patient.age <= 12 && drug.suggestedDosePediatric != "Restricted" &&
<MenuItem key={drug._id} onClick={()=>handleClick(drug)} value={drug.value}>{drug.name}</MenuItem>
}
{ patient.age > 12 &&
<MenuItem key={drug._id} onClick={()=>handleClick(drug)} value={drug.value}>{drug.name}</MenuItem>
}
</>
: null)}
</span>)
)}

最新更新