【问题标题】:how to get duplicate items from a list in vb.net如何从 vb.net 中的列表中获取重复项
【发布时间】:2012-06-05 20:01:28
【问题描述】:

我有一个列表(字符串)。例如:{“C1”、“C12”、“C10”、“C1”、“C6”、“C22”、“C1”、“C6”}。我正在尝试编写一个函数来给我一个重复列表:列表中的 {"C1", "C6"}。每个重复项只会列出一次。我写的函数确实给了我任何回报。我不知道为什么。任何帮助或替代方法表示赞赏。仅供参考,我在 C# 中看到了一个非常相似的问题,但我不知道如何将该语法转换为 VB.net,因为我还没有跟上 LINQ 的速度。在这里:How to get duplicate items from a list using LINQ?

    ''' <summary>
    ''' Given a List(Of String), returns a list of items that are duplicated in the list.
    ''' Each duplicate returned is unique.
    ''' </summary>
    ''' <param name="Set1"></param>
    ''' <returns></returns>
    ''' <remarks></remarks>
    Public Shared Function GetDuplicateItems(ByVal Set1 As List(Of String)) As List(Of String)
        Dim DistinctItems As IEnumerable(Of String)
        'Dim DistinctResults As New List(Of String)
        Dim DuplicateItems As IEnumerable(Of String)
        Dim ItemsToReturn As New List(Of String)

        'Get a set of unique items in the list
        DistinctItems = Set1.Select(Function(x) x).Distinct()
        'Do I need to enumerate the result in order to force the thing to execute?
        'See remarks section of http://msdn.microsoft.com/en-us/library/bb300779.aspx
        'For Each Item As String In DistinctItems
        '    DistinctResults.Add(Item)
        'Next
        'Do a set subtraction (Set1 - UniqueItems)
        DuplicateItems = Set1.Except(DistinctItems)

        For Each Item As String In DuplicateItems
            ItemsToReturn.Add(Item)
        Next

        Return ItemsToReturn
    End Function

【问题讨论】:

    标签: .net vb.net linq


    【解决方案1】:

    这与延迟执行无关,您的算法是错误的:Distinct 不返回列表的唯一项,它只是删除重复项。示例:{"C1", "C12", "C10", "C1", "C6", "C22", "C1", "C6"}.Distinct() 在您的情况下产生 {"C1", "C12", "C10", "C6", "C22"}。因此,Set1.Except(DistinctItems) 将始终生成一个空列表。


    这是您问题的替代解决方案。它选择列表中计数大于 1 的所有项目:

    Dim duplicates = list.Where(Function(x) list.Where(Function(y) x = y).Count() > 1).Distinct()
    

    使用示例:

    Dim list As New List(Of String) From {"a", "a", "b", "c", "c"}
    Dim duplicates = list.Where(Function(x) list.Where(Function(y) x = y).Count() > 1).Distinct()
    ' duplicates now contains {"a", "c"}
    

    编辑:使用 GroupBy 的替代解决方案(受 aquinas 启发):

    Dim duplicates = list.GroupBy(Function(x) x).Where(Function(x) x.Count > 1).Select(Function(x) x.Key)
    

    【讨论】:

    • 这行得通,但它是 O(N^2)。在这种情况下,也许 group by 会更有意义?
    • @aquinas:好点,我添加了一个使用 group by 的替代方法(现在复杂性取决于 GroupBy 的实现;-))。
    • @aquinas:糟糕,刚刚看到您添加了自己的答案。回滚和+1。 ;-)
    • 嘿。哎呀。我删除了我的!继续进行编辑,因为您的答案是更完整的 WRT 延迟执行。
    • @Heinzi 我认为您指出了我的算法中的一个问题,但不是您认为的问题。如果 set1 = {“C1”、“C12”、“C10”、“C1”、“C6”、“C22”、“C1”、“C6”} 并且 distinctitems = {“C1”、“C12”、“C10” ", "C6", "C22"} 不设置 1.except(DistinctItems) = {"C1", "C1", "C6"} 如果是这样,那么我很想知道如何使它工作只是为了学习。但我更喜欢你的解决方案。
    猜你喜欢
    • 2018-07-25
    • 1970-01-01
    • 2023-03-16
    • 1970-01-01
    • 2021-01-21
    • 1970-01-01
    • 2020-11-23
    • 1970-01-01
    • 2010-11-26
    相关资源
    最近更新 更多