我原问题的解决方案
多亏了下面Dan的出色答案,我成功地将原来的代码大幅缩减。我放弃了一些最初拥有的灵活性,即使用多个属性而不是静态属性,但这是一个稍后版本的易修复问题,对于代码大小来说是一个显而易见的选择。再次感谢Dan。在这个例子中,我包含了两个forget()
方法,这些方法被包裹在一个Angular Collection工厂中。
Collection.$inject = ['Constructor', 'Article'];
function Collection(Constructor, Article) {
var Model = Article,
Collection = {},
collection = [],
add,
forget;
function Extendable(data, keys) {
Constructor.call(this, data, Model.fillable);
}
Extendable.prototype = Object.create(Constructor.prototype);
Extendable.prototype.constructor = Extendable;
Collection = Extendable.prototype;
collection = Collection.items = [];
add = function(item) {
if (item instanceof Model) {
collection.push(item);
}
};
Collection.add = add;
// EXAMPLE OF SINGLE ID DELETE I.E. SIMPLE VERSION
forget = function(id) {
collection = _.dropWhile(collection, {id: id});
};
Collection.forget = forget;
// OR!!! EXAMPLE OF MULTI ID VALUE || ARRAY
forget = function(id) {
var ids = [];
if (_.isArray(id)) {
ids = id;
} else {
ids.push(parseInt(id));
}
return _.dropWhile(collection, function (n) {
return _.includes(ids, n.id);
});
};
Collection.forget = forget;
// remove rest of factory for brevity sake
return Extendable;
};
开发工具
Angular 1.4.8, lodash 2.x
问题:
我仍在学习 Angular 和 JS。是否有更简洁的方法来删除多个对象实例(例如,Articles 集合中的 Article/s)。forget()
方法接受 1 个参数,可以是字符串、整数或字符串或整数的数组。
示例:
var articleIdsToRemove = [1, '2', 3];
或者
var articleIdsToRemove = 1;
var articles = newCollection();
为了简洁起见,我省略了向集合中添加文章实例的add方法,但假设我们有10个这样的实例,每个实例都有一个id属性。
我的当前方法
- 验证值的类型,如上所述即数组、字符串、整数,并将所有值设置为int类型的数组,即
ids
- 然后遍历id数组,找到
Article
实例的索引,该实例具有propid
,并且等于id
的值 - 如果找到,则将索引推入indices数组。一旦我们有所有匹配的索引,就将其发送给
Array.prototype.remove
以从集合数组中删除多个项。完成后重新对集合进行排序
出于简洁起见,我省略了Angular工厂包装器,但假设所有内容都在名为Collection的Angular工厂中,该工厂注入了一个数据模型是Article的Article工厂。总之,Collection
(articles) 包含许多Article
。
// We set a collections array inside of object to hold all Article instances
collection = Extendable.prototype.items = [];
// NOTE add articles method removed, but assume weve added multiple Article's to collection
forget = function(id) {
var ids = [],
index = null,
indices = [];
if (angular.isDefined(id) && !_.isEmpty(id)) {
ids = _.isArray(id) ? id : isInt(id) ? [Number(id)] : [];
if (ids.length) {
_.each(ids, function(id) {
index = getIndex('app_id', id);
if (index) {
indices.push(index)
}
});
if (indices.length) {
collection = collection.remove(indices)
}
}
}
};
Extendable.prototype.forget = forget;
function isInt(n){
return Number(n) === n && n % 1 === 0;
}
function getIndex(prop, value) {
return _.indexOf(collection, function(d) {
if (hasProp(d, prop)) {
return d[prop] == value;
}
});
}
function hasProp (obj, prop) {
return Object.prototype.hasOwnProperty.call(obj, prop);
}
Array.prototype.remove = function(){
var args = Array.apply(null, arguments);
var indices = [];
for(var i = 0; i < args.length; i++){
var arg = args[i];
var index = this.indexOf(arg);
while(index > -1){
indices.push(index);
index = this.indexOf(arg, index + 1);
}
}
indices.sort();
for(var i = 0; i < indices.length; i++){
var index = indices[i] - i;
this.splice(index, 1);
}
};
forget(['4',3'])
不会删除任何内容。我认为使用_.reject
更合适,而不是_.dropWhile
。 - steezeburger