简体   繁体   English

C#:如何比较两个集合(System.Collection.Generic.List <T> )使用Linq / Lambda?

[英]C# : How to compare two collections (System.Collection.Generic.List<T>) using Linq/Lambda?

I'm having two collections of String like 我有两个String集合

 List<String> l_lstOne = new List<String> { "100", "1X0", "X11", "XXX" }, 
    l_lstTwo = new List<String> { "000", "110", "100", "000" };

I need to compare the two lists and make the second list like 我需要比较两个列表并使第二个列表像

    { "000", "1X0", "X00", "XXX" }

Note: Both the list will contain same numbe of elements and the length of each element will be same. 注意:列表中的两个元素都包含相同的元素,每个元素的长度都相同。

The comparision is like 比较就像

  1. If an mth element in l_lstOne have an 'X' in nth position, the the nth position of the mth in l_lstTwo should be replaced by 'X'. 如果l_lstOne的第m个元素在第n个位置具有“X”,则l_lstTwo中第m个的第n个位置应替换为“X”。

Example

    l_lstOne            l_lstTwo        Output

      100                 000             000
      1X0                 110             1X0
      X11                 100             X00

So, to solve this i used nested for loop , here is my source code, 所以,为了解决这个问题,我使用了嵌套for循环,这是我的源代码,

 for (int l_nIndex = 0; l_nIndex < l_lstTwo.Count; l_nIndex++)
        {
            String l_strX = String.Empty;

            for (int l_nInnerIndex = 0; l_nInnerIndex < l_lstTwo[l_nInnerIndex].Length; l_nInnerIndex++)
            {
                l_strX += l_lstOne[l_nIndex][l_nInnerIndex] == 'X' ? 'X' : l_lstTwo[l_nIndex][l_nInnerIndex];
            }
            l_lstTwo[l_nIndex] = l_strX;
        }   

This code is working fine, but the thing is, its taking more time to execute, ie almost 600 milliseconds to process 200000 elements and each of length 16. 这段代码运行正常,但问题是,它需要花费更多的时间来执行,即处理200000个元素和16个长度的每个元素几乎600毫秒。

And moreover i need a Linq or Lambda method to resolve this. 此外,我需要一个Linq或Lambda方法来解决这个问题。 So please help me to do this. 所以请帮我这样做。 Thanks in advance. 提前致谢。

LINQ will not help you here; LINQ在这里不会帮到你; LINQ is not meant to modify collections. LINQ不是要修改集合。

You can make your code substantially faster by building a char[] instead of a string ; 您可以通过构建char[]而不是string来使代码大大加快; right now, you're building 3.2 million string objects because of the += . 现在,由于+= ,你正在构建320万个string对象。

Instead, you can write 相反,你可以写

char[] l_strX = new char[l_lstTwo[l_nInnerIndex].Length];

for (int l_nInnerIndex = 0; l_nInnerIndex < l_lstTwo[l_nInnerIndex].Length; l_nInnerIndex++)
{
    l_strX[l_nInnerIndex] = l_lstOne[l_nIndex][l_nInnerIndex] == 'X' ? 'X' : l_lstTwo[l_nIndex][l_nInnerIndex];
}
l_lstTwo[l_nIndex] = new string(l_strX);

Mh, if I understand it correctly the words in l_lstOne act as a mask for the words in l_lstTwo where the mask is transparent unless it's an X . 嗯,如果我理解正确的话, l_lstOne的单词充当l_lstTwo中单词的掩码,其中掩码是透明的,除非它是X How about this: 这个怎么样:

l_lstOne.Zip(l_lstTwo, 
    (w1, w2) => new String(w1.Zip(w2, (c1, c2) => c1 == 'X' ? c1 : c2).ToArray())))

Zip is a Linq extension method available from .NET 4 on which combines the elements of two lists like a zip. Zip是一种可从.NET 4获得的Linq扩展方法 ,它结合了两个列表的元素,如zip。 The outer zip basically creates the word pairs to iterate over and the second one creates a the mask (take all characters from the second word unless word one has an X in that position). 外拉链基本上创建了单词对以进行迭代,第二个创建了一个蒙版(从第二个单词中取出所有字符,除非第一个单词在该位置有一个X )。

Also note that this creates a new sequence of strings rather than replacing the ones in l_lstTwo - that's the Linq way of doing things. 还要注意,这会创建一个新的字符串序列,而不是替换l_lstTwo中的l_lstTwo - 这就是Linq的处理方式。

You could do it with the following statement in .NET 3.5 您可以使用.NET 3.5中的以下语句执行此操作

    IEnumerable <String> result =
        Enumerable.Range(0, l_lstOne.Count)
            .Select(i => Enumerable.Range(0, l_lstOne[i].Length)
                .Aggregate(string.Empty, (innerResult, x) => innerResult += l_lstOne[i][x] == 'X' ? 'X' : l_lstTwo[i][x]));

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 Linq过滤了一个IQueryable <T> (System.Data.Linq.DataQuery)对象由List <T> (System.Collection.Generic.List)对象? - Linq filtering an IQueryable<T> (System.Data.Linq.DataQuery) object by a List<T> (System.Collection.Generic.List) object? 错误-使用通用类型&#39;System.Collection.Generic.List <T> 需要&#39;1&#39;类型的参数 - Error - Using the generic type 'System.Collection.Generic.List<T> requires '1' type arguments 无法转换类型System.Collection.Generic.List <T> - Cannot Convert Type System.Collection.Generic.List<T> 无法从&#39;System.Collections.Generic.IEnumerable转换 <System.Collection.Generic.List<char> &gt;字符串[] - Cannot convert from 'System.Collections.Generic.IEnumerable<System.Collection.Generic.List<char>> to string[] 转换短吗? 到System.Collection.Generic.List - Convert Short? to System.Collection.Generic.List 无法将System.Linq.IOrderedQuerable转换为System.Collection.Generic.List错误 - Can not convert System.Linq.IOrderedQuerable to System.Collection.Generic.List error 我如何转换 &#39;System.Collection.Generic.List<String> &#39; 到 &#39;System.Windows.Documents.List&#39;? - How can I convert 'System.Collection.Generic.List<String>' into 'System.Windows.Documents.List'? 在 C# 中使用 linq 比较两个列表 - Compare two list using linq in C# 如何比较两个List <String> 在C#中使用LINQ - How to compare two List<String> using LINQ in C# C# System.Collections.Generic.List 中的错误<T> ? - Bug in C# System.Collections.Generic.List<T>?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM