【问题标题】:How to subtract one generic list from another in C#2.0如何在 C#2.0 中从另一个通用列表中减去一个通用列表
【发布时间】:2010-02-15 14:52:35
【问题描述】:

首先,很可能是我以错误的方式处理我的问题,在这种情况下,我很乐意接受替代方案。

我想要实现的是检测 USB 设备连接到计算机后创建的驱动器。

这是简化的工作流程:

// Get list of removable drives before user connects the USB cable
List<string> listRemovableDrivesBefore = GetRemovableDriveList();

// Tell user to connect USB cable
...

// Start listening for a connection of a USB device
...

// Loop until device is connected or time runs out
do
{
    ...
} while

// Get list of removable drives after USB device is connected
List<string> listRemovableDrivesAfter = GetRemovableDriveList();

// Find out which drive was created after USB has been connected
???

GetRemovableDriveList 返回可移动驱动器号的字符串列表。 我的想法是获取一个可移动驱动器列表之前设备连接,另一个列表之后它连接,并且通过从第一个列表的内容中删除其次,我会留下刚刚连接的驱动器(通常只有一个)。

但我找不到从另一个列表中“减去”一个列表的简单方法。任何人都可以提出解决方案,甚至是更好的方法来实现我正在尝试做的事情。

注意:项目面向 .NET 框架 2.0,因此无法使用 LINQ。

谢谢!

【问题讨论】:

    标签: c# windows c#-2.0 device-driver generic-list


    【解决方案1】:

    执行此操作的一般方法是将源集合中的所有项目添加到字典中,然后删除另一个集合中的项目:

    public static IEnumerable<T> Subtract<T>(IEnumerable<T> source, IEnumerable<T> other)
    {
        return Subtract(source, other, EqualityComparer<T>.Default);
    }
    
    public static IEnumerable<T> Subtract<T>(IEnumerable<T> source, IEnumerable<T> other, IEqualityComparer<T> comp)
    {
        Dictionary<T, object> dict = new Dictionary<T, object>(comp);
        foreach(T item in source)
        {
            dict[item] = null;
        }
    
        foreach(T item in other)
        {
            dict.Remove(item);
        }
    
        return dict.Keys;
    }
    

    【讨论】:

    • 一种有效的解决方案,但方法名称错误。它不返回两个序列的交集。
    • 在我看来这两个答案都是有效的,但由于我的要求,我选择了简单的方法。
    【解决方案2】:

    对于少量元素,带有Contains 调用的foreach 循环应该可以解决问题:

    List<string> listRemovableDrivesBefore = GetRemovableDriveList();
    // ...
    List<string> listRemovableDrivesAfter = GetRemovableDriveList();
    
    List<string> addedDrives = new List<string>();
    foreach (string s in listRemovableDrivesAfter)
    {
        if (!listRemovableDrivesBefore.Contains(s))
            addedDrives.Add(s);
    }
    

    如果集合有很多元素,那么您可以使用Dictionary&lt;K,V&gt; 而不是List&lt;T&gt; 来提高查找效率。 (理想情况下,您应该使用 HashSet&lt;T&gt;,但这在框架的版本 2 中不可用。)

    【讨论】:

    • 我选择了这个答案,因为我需要一次性的东西。如果我需要在不同的地方重复执行此操作,我可能会实施从 Lee 的答案中减去。
    【解决方案3】:

    您可以使用 Linq 扩展方法的 SubtractInsersect,就像使用数学集一样。

    A = 原始。

    B = 之后。

    A - (A Intersect B) = 从原始数据中删除 B - (A 插入 B) = 新

    var intersect = A.Intersect(B);

    var 已移除 = A.Substract(intersect); var new = B.Substract(intersect)

    希望这对你有用。

    【讨论】:

    • Linq 没有称为 Subtract(或 Substract)的方法。我想你的意思是Except
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-07-06
    • 1970-01-01
    • 2011-07-02
    • 1970-01-01
    • 2012-08-19
    • 2023-01-07
    相关资源
    最近更新 更多