3

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

1 回答 1

9

这与延迟执行无关,您的算法是错误的: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)
于 2012-05-31T14:55:01.027 回答