Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/json/13.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript Lodash:按多个特性过滤嵌套对象_Javascript_Json_Lodash - Fatal编程技术网

Javascript Lodash:按多个特性过滤嵌套对象

Javascript Lodash:按多个特性过滤嵌套对象,javascript,json,lodash,Javascript,Json,Lodash,考虑以下示例: var products = { "Products": [{ "Title": "A", "Categories": [{ "Name": "Type", "Properties": ["Type 1", "Type 2", "Type 3"] }, { "Name": "Market", "Properties": ["Mar

考虑以下示例:

var products = {
    "Products": [{
        "Title": "A",
        "Categories": [{
            "Name": "Type",
            "Properties": ["Type 1", "Type 2", "Type 3"]
        }, {
            "Name": "Market",
            "Properties": ["Market 1", "Market 2", "Market 3", "Market 4"]
        }, {
            "Name": "Technology",
            "Properties": ["Tech 1", "Tech 2"]
        }]
    }, {
        "Title": "B",
        "Categories": [{
            "Name": "Type",
            "Properties": ["Type 1", "Type 3"]
        }, {
            "Name": "Market",
            "Properties": "Market 1"
        }, {
            "Name": "Technology",
            "Properties": ["Tech 1", "Tech 3"]
        }]
    }, {
        "Title": "C",
        "Categories": [{
            "Name": "Type",
            "Properties": ["Type 1", "Type 2", "Type 3"]
        }, {
            "Name": "Market",
            "Properties": ["Market 2", "Market 3"]
        }, {
            "Name": "Technology",
            "Properties": ["Tech 2", "Tech 3"]
        }]
    }]
}

我试图通过属性过滤产品,所以考虑我使用一个数组来跟踪我所选的过滤器:

var filters = ['Type 3', 'Tech 1'];
使用这些过滤器,我想返回产品A和产品B

我目前有:

var flattenedArray = _.chain(products).map('Categories').flatten().value();
var result= _.some(flattenedArray , ['Properties', 'Tech 1']);
但是,我一直在研究如何组合属性进行组合搜索。

使用
\uu.filter()
迭代产品。对于每个产品,使用
.flatMap()
组合属性列表,并使用
.intersection()
.size()
查找类别中存在的过滤器数量。将其与过滤器的原始数量进行比较,并返回比较的响应

var产品={“产品”:[{“标题”:“A”,“类别”:[{“名称”:“类型”,“属性”:[“类型1”,“类型2”,“类型3”]},{“名称”:“市场”,“属性”:[“市场1”,“市场2”,“市场3”,“市场4”]},{“名称”:“技术”,“属性”:[“技术1”,“技术2”]}},{“标题”:“B”,“类别”:[{“名称”:“类型”,“属性”:“类型”,“类型1”,“类型3”},{“名称”:“市场”,“财产”:“市场1”},{“名称”:“技术”、“财产”:[“技术1”、“技术3”]},{“名称”:“C”、“类别”:[{“名称”:“类型”、“财产”:[“类型1”、“类型2”、“类型3”]},{“名称”:“市场”、“财产”:[“市场2”、“市场3”]},{“名称”:“技术”、“财产”:[“技术2”、“技术3”]}};
变量过滤器=['Type 3','Tech 1'];
var结果=551;.filter(products.products,函数(product){
return filters.length===(product.Categories)
.flatMap(“属性”)
.交叉口(过滤器)
.size();
});
console.log(结果);
使用
.filter()
迭代产品。对于每个产品,使用
.flatMap()
组合属性列表,并使用
.intersection()
.size()
查找类别中存在的筛选器数量。将其与原始筛选器数量进行比较,然后返回比较结果

var产品={“产品”:[{“标题”:“A”,“类别”:[{“名称”:“类型”,“属性”:[“类型1”,“类型2”,“类型3”]},{“名称”:“市场”,“属性”:[“市场1”,“市场2”,“市场3”,“市场4”]},{“名称”:“技术”,“属性”:[“技术1”,“技术2”]}},{“标题”:“B”,“类别”:[{“名称”:“类型”,“属性”:“类型”,“类型1”,“类型3”},{“名称”:“市场”房地产“:”市场1“},{”名称“:”技术“,”房地产“:[”技术1“,”技术3“]},{”标题“:”C“,”类别“:[{”名称“:”类型“,”房地产“:”[”类型1“,”类型2“,”类型3“]},{”名称“:”市场“,”房地产“:”,“{”名称“:”技术“,”房地产“:[”技术2“,”技术3“]}]};
变量过滤器=['Type 3','Tech 1'];
var结果=551;.filter(products.products,函数(product){
return filters.length===(product.Categories)
.flatMap(“属性”)
.交叉口(过滤器)
.size();
});
console.log(结果);

如果我正确理解您的问题,此代码可能有助于:

_.filter(
    products.Products,
    product => _.difference(
        filters,
        _.chain(product.Categories).map(category => category.Properties).flatten().value()
    ).length === 0
);
它计算每个产品的所有属性的并集:

_.chain(product.Categories).map(category => category.Properties).flatten().value()
然后,使用
\uu0.difference
方法检查它是否包含所有
过滤器
数组元素


希望有帮助。

如果我正确理解您的问题,此代码可能会有帮助:

_.filter(
    products.Products,
    product => _.difference(
        filters,
        _.chain(product.Categories).map(category => category.Properties).flatten().value()
    ).length === 0
);
它计算每个产品的所有属性的并集:

_.chain(product.Categories).map(category => category.Properties).flatten().value()
然后,使用
\uu0.difference
方法检查它是否包含所有
过滤器
数组元素


希望能有帮助。

另一种奇特的方式


另一种奇特的方式


这适用于要筛选的给定属性为类似“DoorColor”的字符串或表示给定属性路径的字符串数组的项目列表,如['town'、'street'、'DoorColor'],用于嵌套在项目上的值town.street.DoorColor

它还可以过滤多个值,因此您只需要传入一个表示要保留的字符串值的子字符串数组,它将保留具有字符串值的项,该字符串值包含子字符串数组中的任何子字符串

最后一个参数“includes”确保保留这些值,如果将其设置为false,则它将排除这些值,并保留没有在子字符串数组中指定的任何值的值

import { flatMap, path } from 'lodash/fp';

const filteredListForItemsIncludingSubstringsOnAGivenProperty = (items, givenProperty, substrings, including=true) => flatMap((item) =>
substrings.find((substring) => path(givenProperty)(item) && path(givenProperty)(item).includes(substring))
  ? including
    ? [item]
    : []
  : including
  ? []
  : [item])(items);
例如,fLFIISOAGP(联系人,['person','name',['Joh','Pau',Pet']; 结构为{contact,business:null,personal:{name:'John'}的项目

对于最初的问题-这也会起作用-我会在项目列表上重复使用它,使用不同的键过滤多个属性

const firstFilteredResult=FilteredListForItems包括给定属性的子字符串(
产品,产品,,
[“类别”、“0”、“属性”],
[“类型3”];

const secondFilteredResult=FilteredListForItems包括给定属性的子字符串(
FirstFiltereResult,
[“类别”、“2”、“属性”],
[“Tech 1”];


expect(secondFilteredResult[0]['Title']).to.equal(“A”);
期望(secondFilteredResult[1]['Title'])等于(B);

expect(secondFilteredResult.length).to.equal(2);

这将适用于要筛选的给定属性为类似“doorcolor”的字符串或表示给定属性路径的字符串数组的项目列表,例如['town'、'street'、'doorcolor',用于嵌套在项目上的值town.street.doorcolor

它还可以过滤多个值,因此您只需要传入一个表示要保留的字符串值的子字符串数组,它将保留具有字符串值的项,该字符串值包含子字符串数组中的任何子字符串

最后一个参数“includes”确保保留这些值,如果将其设置为false,则它将排除这些值,并保留没有在子字符串数组中指定的任何值的值

import { flatMap, path } from 'lodash/fp';

const filteredListForItemsIncludingSubstringsOnAGivenProperty = (items, givenProperty, substrings, including=true) => flatMap((item) =>
substrings.find((substring) => path(givenProperty)(item) && path(givenProperty)(item).includes(substring))
  ? including
    ? [item]
    : []
  : including
  ? []
  : [item])(items);
例如,fLFIISOAGP(联系人,['person','name'],['Joh','