2016-09-28 68 views
1

我想使用underscoreJs操纵JavaScript对象,并有问题这样做。深入采摘使用Underscore.JS

这是我的例子

var data = { 
 
    "label": "SomeName", 
 
    "parent": [{ 
 
    "id": "parentId", 
 
    "resources": [{ 
 
     "name": "ID1NAME", 
 
     "calls": [ 
 
     "user_get", "user2_post", "user3_delete" 
 
     ] 
 
    }, { 
 
     "name": "ID2", 
 
     "calls": [ 
 
     "employee1_get", "employee2_delete", "employee3_update" 
 
     ] 
 
    }] 
 
    }] 
 
}; 
 
var res = _(data).chain(). 
 
    pluck('parent'). 
 
    flatten(). 
 
    findWhere(function(item){ 
 
    item === "user_get" 
 
    }). 
 
    value(); 
 
    
 
console.log(res);

使用一个元件,其是data.parent.calls[]的一部分(例如: “user_get”)我想以提取它的父对象,即data.parent[0]

我上面试过但总是弄不明白。我很感激这方面的帮助。

+0

你有没有机会将JSON包装到数组中?由于Underscore正在使用集合(它包含一个包含所有类型对象的数组),因此将JSON写入数组可以解决您的问题。 https://codepen.io/anon/pen/WGroRm?editors=0011 – Aer0

+0

@torazburo感谢您的建议。我确定知道解析和JSON的含义。我可能错误地使用了解析这个词,但是我打算将它称为JSON文档是正确的,因为我一直在处理JSON文档。我通过跳过将JSON文档解析为Javascript对象的部分给出了一个示例。 此外,在适当的尊重,操纵你使用的词是不正确的,提取会很好。我尊重他人:) –

回答

1

一个你遇到的问题是你的_.pluck使用。如果在对象上执行_.pluck,它将检查对象的键,试图检索您指定的属性作为第二个参数(在此例中为的父')。 'label'是一个字符串,'父'是一个数组,因此您得到的数组结果为[undefined, undefined]。其余的则会出错。

一种解决方案可以如下:

function findCallIndexInParent(call, parent) { 
    return _.chain(parent) 
      .pluck('resources') 
      .flatten() 
      .findIndex(function (obj) { 
       return _.contains(obj.calls, call); 
      }) 
      .value(); 
} 

function findCall(call, data) { 
    var parent = data.parent; 
    return parent[findCallIndexInParent(call, parent)]; 
} 

console.log(findCall('user_get', data)); 

findCall仅仅是将数据的父属性传递给findCallIndexInParent(将检索其中呼叫是索引)的便利方法和返回所需对象与父类数组。

Lodash(下划线的一个分支)提供了一种方法来获得一个对象的属性,在这里真的很方便(可惜,下划线没有)。

findCallIndexInParent的解释如下:

  1. 链父列表
  2. 摘去资源阵列
  3. 作为拔毛地图,它返回所以需要一个扁平化列表的列表。
  4. 查找其调用包含包含呼叫内的对象的呼叫
  5. 返回的值(指数)的元素的索引。

这是fiddle。希望能帮助到你。

+0

感谢您的明确解释。感谢你的时间和帮助。 –

1

这似乎是个伎俩。

function findByCall(data, call) { 
 
    return _.find(data.parent, function(parent) {   //From data.parent list, find an item that 
 
    return _.some(parent.resources, function(resource) {//has such parent.resource that it 
 
     return _.includes(resource.calls, call);   //includes the searched resource.calls item 
 
    }); 
 
    }); 
 
} 
 

 
//Test 
 

 
var data = { 
 
    "label": "SomeName", 
 
    "parent": [{ 
 
    "id": "parentId", 
 
    "resources": [{ 
 
     "name": "ID1NAME", 
 
     "calls": [ 
 
     "user_get", "user2_post", "user3_delete" 
 
     ] 
 
    }, { 
 
     "name": "ID2", 
 
     "calls": [ 
 
     "employee1_get", "employee2_delete", "employee3_update" 
 
     ] 
 
    }] 
 
    }] 
 
}; 
 

 
console.log(findByCall(data, 'user_get'));
<script src="https://cdnjs.cloudflare.com/ajax/libs/underscore.js/1.8.3/underscore.js"></script>

+0

我感谢你的帮助。 –

1

如果我理解正确,您想获取parent数组中具有指定调用资源的元素的索引。

data = { 
 
    "label": "SomeName", 
 
    "parent": [{ 
 
    "id": "parentId", 
 
    "resources": [{ 
 
     "name": "ID1NAME", 
 
     "calls": [ 
 
     "user_get", "user2_post", "user3_delete" 
 
     ] 
 
    }, { 
 
     "name": "ID2", 
 
     "calls": [ 
 
     "employee1_get", "employee2_delete", "employee3_update" 
 
     ] 
 
    }] 
 
    }] 
 
} 
 

 
// find the index of a parent 
 
const index = _.findIndex(data.parent, parent => 
 
    // that has any (some) resources 
 
    _.some(parent.resources, resource => 
 
     // that contains 'user_get' call in its calls list 
 
     _.contains(resource.calls, 'user_get') 
 
    ) 
 
) 
 

 
console.log(index) // 0
<script src="https://cdnjs.cloudflare.com/ajax/libs/underscore.js/1.8.3/underscore-min.js"></script>

如果你想找到实际的父对象,如果你想找到匹配这个调用所有父对象使用find代替findIndex

,用filter代替findIndex