2015-12-21 162 views
3

嗨我想删除阵列内的数组内的元素。 我的模式是:删除阵列内数组元素

var mySchema = Schema({ 
    primaryField:String, 
    list1: [{ 
    item1: String, 
    item2:String 
    }], 
    list2 : [{ 
    item3:String, 
    item4 : [String]//item4 is string values available in item1 
    }] 
}); 

为前:

{ 
    "primaryField": "abc", 
    "list1": [{ 
    "item1": "aa", 
    "item2": "mystring" 
    },{ 
    "item1": "bb", 
    "item2": "sampStr" 
    }], 
    "list2": [{ 
    "item3": "stringitem", 
    "item4": ["aa", "bb"] 
    },{ 
    "item3": "sample", 
    "item4": ["bb"] 
    },{ 
    "item3": "samplestring", 
    "item4": ["aa"] 
    }] 
} 

我不得不删除list1"aa"项目和"aa"list2.item4的发生,如果只是"aa"存在于item4然后我要删除整个对象条目。

我的输出应该是:

{ 
    "primaryField": "abc", 
    "list1": [{ 
    "item1": "bb", 
    "item2": "sampStr" 
    }], 
    list2:[{ 
    "item3": "stringitem", 
    "item4": ["bb"] 
    },{ 
    "item3": "sample", 
    "item4": ["bb"] 
    }] 
} 

任何人都可以帮助我实现这一目标如何使用Node.js和猫鼬。架构不能修改。

回答

1

这产生了预期的输出。它应该足够通用,而且我不确定它是否可以与您的代码一起工作,但是考虑到问题中指定的内容,我认为它应该没问题。

function removeAllItems(obj, value) { 
    var deleted; 

    if (!obj) { 
    return false; 
    } 

    if (obj === value) { 
    deleted = true; 
    } else if (Array.isArray(obj)) { 
    for (var i = 0, len = obj.length; i < len; ++i) { 
     if (removeAllItems(obj[i], value)) { 
     obj.splice(i--, 1); 

     if (!obj.length) { 
      deleted = true; 
     } 
     } 
    } 
    } else if (typeof obj === 'object') { 
    for (var keys = Object.keys(obj), key, i = 0, len = keys.length; i < len; ++i) { 
     if (removeAllItems(obj[keys[i]], value)) { 
     delete obj[keys[i]]; 

     deleted = true; 
     } 
    } 
    } 

    return deleted; 
} 

测试用:

var test = { 
    "primaryField": "abc", 
    "list1": [{ 
    "item1": "aa", 
    "item2": "mystring" 
    },{ 
    "item1": "bb", 
    "item2": "sampStr" 
    }], 
    "list2": [{ 
    "item3": "stringitem", 
    "item4": ["aa", "bb"] 
    },{ 
    "item3": "sample", 
    "item4": ["bb"] 
    },{ 
    "item3": "samplestring", 
    "item4": ["aa"] 
    }] 
}; 

var valueToRemove = 'aa'; 

removeAllItems(test, valueToRemove); 
console.log('Removing all', valueToRemove, JSON.stringify(test, null, 2)); 

给出结果

Removing all aa { 
    "primaryField": "abc", 
    "list1": [ 
    { 
     "item1": "bb", 
     "item2": "sampStr" 
    } 
    ], 
    "list2": [ 
    { 
     "item3": "stringitem", 
     "item4": [ 
     "bb" 
     ] 
    }, 
    { 
     "item3": "sample", 
     "item4": [ 
     "bb" 
     ] 
    } 
    ] 
} 

下面是考虑到循环引用的更新,并且如果任何值被移除返回true,或false否则。

function removeAllItems(obj, value) { 
    var stack = []; 
    var found = false; 

    function _next(obj) { 
    var deleted; 

    if (!obj) { 
     return false; 
    } else if (stack.indexOf(obj) >= 0) { 
     return false; // cyclical reference found 
    } 

    stack.push(obj); 

    if (obj === value) { 
     found = deleted = true; 
    } else if (Array.isArray(obj)) { 
     for (var i = 0, len = obj.length; i < len; ++i) { 
     if (_next(obj[i])) { 
      obj.splice(i--, 1); 

      if (!obj.length) { 
      deleted = true; 
      } 
     } 
     } 
    } else if (typeof obj === 'object') { 
     for (var keys = Object.keys(obj), key, i = 0, len = keys.length; i < len; ++i) { 
     if (_next(obj[keys[i]])) { 
      delete obj[keys[i]]; 

      deleted = true; 
     } 
     } 
    } 

    stack.pop(); 

    return deleted; 
    } 

    return _next(obj), found; 
} 
+0

感谢您的回复。当我尝试直接使用示例数据时,它工作正常。但是当我通过find()查询[model.find({condition},function(error,result)]的输出时,它会抛出RangeError:超出最大调用堆栈大小。如果您有任何想法这个我不确定我在数据中犯的错误 – Nizam

+0

如果没有产生这个错误的样本数据很难说,如果你能提供一个错误的集合,那么我会知道为什么你会得到这个错误,我可以尝试查看我的建议......但乍一看,它应该与您指定的内容相符 –

+0

我可以看到的唯一情况是,如果您在数据中有循环引用... –