我对List<T>.Remove(T)方法有一些问题。我有一个类(向下描述),它用作列表的类型。
我的课是:
public class MyClass
{
public string ID { get; set; }
public myEnum CallType { get; set; }
public object ObjToStore { get; set; }
}我的List<T>被实例化如下:
private static List<MyClass> ListOfStoreObjects = new List<MyClass>();我的麻烦是,我把这些东西存储在这些清单中,我不能把它们删除。我使用这些列表将临时数据存储在web服务中(我想要“走这条路”,所以请不要告诉我其他解决方案,thx),当然,一旦使用了这些数据,我就必须设法将它们从这个“缓冲区”中删除。那么,有一种方法可以从静态列表中删除元素吗?
编辑
我使用的add函数是:
public bool AddToQueue(string id, myEnum callType, object objToAdd)
{
try
{
MyClass elementToAdd = new MyClass();
elementToAdd.ID = id;
elementToAdd.CallType = callType;
elementToAdd.ObjToStore = objToAdd;
ListOfStoreObjects.Add(elementToAdd);
return true;
}
catch
{
return false;
}
}用于检索所需对象的函数,然后从列表中删除它:
public object RetrieveObj(string id, myEnum callType)
{
object obj = null;
foreach(var element in ListOfStoreObjects)
{
if( element.ID == id && element.CallType == callType)
{
obj = element.ObjToStore;
break;
}
}
MyClass itemToRemove = new MyClass();
itemToRemove.ID = id;
itemToRemove.CallType = callType;
itemToRemove.ObjToStore = obj;
ListOfStoreObjects.Remove(itemToRemove);
return obj;
}发布于 2017-05-02 12:19:36
您正在错误地移除该对象。你必须这样移除它:
public MyClass RetrieveObj(string id, myEnum callType)
{
MyClass obj = null;
foreach(var element in ListOfStoreObjects)
{
if( element.ID == id && element.CallType == callType)
{
obj = element;
break;
}
}
ListOfStoreObjects.Remove(obj);
return obj;
}这是一个很常见的错误。您正在查找正确的对象,而不是使用该实例,而是创建类的一个新对象,该对象将永远不会与列表中的任何对象匹配。
交替解
分享一种简单的单行方式来完成您想要做的事情:
ListOfStoreObjects.RemoveAll(x => x.ID == id && x.CallType == callType);发布于 2017-05-02 12:01:19
您需要实现IEquatable<T>,通用List<T>集合在内部使用它来确定自定义类型的相等性。
下面是一个示例(假设ID是您唯一的标识符):
public class MyClass : IEquatable<MyClass>
{
public string ID { get; set; }
public myEnum CallType { get; set; }
public object ObjToStore { get; set; }
public bool Equals(MyClass x)
{
return x.ID.Equals(this.ID);
}
}编辑
创建一个与尝试删除的对象不共享引用相等的新对象。上面所提供的方法可以做到这一点,但对于您的情况,它并不是最干净的解决方案。
我建议移除index,但前提是你更喜欢使用List而不是HashSet。
for(int i = 0; i < ListOfStoreObjects.Count; i++)
{
if( ListOfStoreObjects[i].ID == id && ListOfStoreObjects[i].CallType == callType)
{
ListOfStoreObjects.RemoveAt(i);
break;
}
}为什么RemoveAt而不是Remove?Array作为List的基础集合,O(1)按索引查找元素,因此对于这种类型的集合来说,由于数组在内存中解析的语义,它是删除项的最有效方法。另外,如果要查看.NET源代码,Remove方法将再次遍历collection并删除调用Equals方法的元素,以检查是否相等。
发布于 2017-05-02 12:00:52
理想情况下,Remove()应该工作,并且是一种更好和正确的方法。你应该试着找出为什么你没有正确地使用它。但是,如果你仍然不能,你可以尝试这样的东西。您应该用另一个条件替换st.IsCompleted,以指示不移除该项。请注意,这并不像Remove()那样有效,只是作为一种解决办法。
ListOfStoreObjects = ListOfStoreObjects.Where(st => st.IsCompleted).ToList();https://stackoverflow.com/questions/43737160
复制相似问题