简体   繁体   English

C#比较两个有序列表以获取更新的值

[英]C# Compare two ordered lists for updated values added

I have a data source containing say, 6 items, order important, which updates each time I check it. 我有一个数据源,其中包含6个重要订单,每次检查时都会更新。
Here is the initial list 这是初始清单
List 1: 清单1:

  • dog
  • cat
  • fish
  • cat
  • cat
  • mouse 老鼠

I then wait, the list updates some amount with the top items being removed and new ones added. 然后,我等待,列表更新了一些内容,其中删除了最重要的项目,并添加了新项目。 Here is the new list I fetch. 这是我获取的新列表。
List 2: 清单2:

  • fish
  • cat
  • cat
  • mouse 老鼠
  • cat
  • hamster 仓鼠

I would like a way of finding out the new values which were added, cat + hamster in this case. 我想找出一种新添加的值,在这种情况下为cat +仓鼠。

My actual problem has a source of 38 items and each check, between 0 - 38 items have been added to the bottom. 我的实际问题有38个项目的来源,每张支票的底部都添加了0-38个项目。 I cannot view any more than the latest 38 items however. 我只能查看最新的38个项目。

Example

        List<string> list1 = new List<string>();
        List<string> list2 = new List<string>();

        list1.Add("dog");
        list1.Add("cat");
        list1.Add("fish");
        list1.Add("cat");
        list1.Add("cat");
        list1.Add("mouse");

        list2.Add("fish");
        list2.Add("cat");
        list2.Add("cat");
        list2.Add("mouse");
        list2.Add("cat");
        list2.Add("hamster");

        Console.WriteLine("List 1" + Environment.NewLine);

        foreach(string item in list1)
        {
            Console.WriteLine(item);
        }

        Console.WriteLine(Environment.NewLine + "List 2" + Environment.NewLine);

        foreach (string item in list2)
        {
            Console.WriteLine(item);
        }

        var newItems = list2.Except(list1);

        Console.WriteLine(Environment.NewLine + "New Items" + Environment.NewLine);

        foreach (string item in newItems)
        {
            Console.WriteLine(item);
        }

Using Except, the result is 'hamster' as cat did exist in the first list and except does not seem to check order (Is there a way?) 使用Except,结果是“仓鼠”,因为猫确实存在于第一个列表中,但似乎并没有检查顺序(有办法吗?)

Now, this seems easy and like it should have been answered so I presume I'm just not typing the right thing into search. 现在,这似乎很容易,应该已经回答了,所以我想我只是没有在搜索中输入正确的内容。

Any help appreciated. 任何帮助表示赞赏。

EDIT I can imagine a solution by looping through lists of increasing size, starting with the last value of list 1 and the first value of list 2 and then using SequenceEqual() until false to count how many items overlap and going from there. 编辑我可以想像一个解决方案,它会循环遍历大小递增的列表,从列表1的最后一个值和列表2的第一个值开始,然后使用SequenceEqual()直到为false来计算有多少项重叠并从那里开始。 Would this be a good solution? 这将是一个好的解决方案吗?

Solution Used I did as mentioned in my edit and looped through comparing lists of increasing size for a match using SequenceEqual() 使用的解决方案我做了我在编辑中提到的操作,并使用SequenceEqual()遍历了比较大小增加的列表以进行匹配

Im sure this is inefficient but this wont pose as issue for me. 我确定这是低效的,但这对我来说不是问题。 If anyone does know a neater trick, that would be great. 如果有人知道更巧妙的技巧,那将是很棒的。

        int size1 = list1.Count();
        int size2 = list2.Count();

        int i;
        for (i = 1; i <= size2; i++)
        {
            List<string> aList = list1.GetRange(size1 - i, i);
            List<string> bList = list2.GetRange(0, i);
            if(aList.SequenceEqual(bList))
            {
                break;
            }
        }

        int totalAdded = size2 - i;
        List<string> newItemsList = list2.GetRange(i, totalAdded);

        foreach (string item in newItemsList)
        {
            Console.WriteLine(item);
        }

        Console.ReadLine();

If I understand you correctly, you are looking to create a third list with the new items? 如果我对您的理解正确,那么您是否希望使用新项目创建第三个列表? Or at least find the new items: 或至少找到新项目:

List<string> newItems = new List<string>();
newItems.AddRange(list2.FindAll(s=> !list1.Contains(s)));

The issue that StriplingWarrior mentioned in the comment is very important. 评论中提到的StriplingWarrior问题非常重要。 Although its possibility is low, but the solution should be the one that works in all cases. 尽管其可能性很小,但是解决方案应该是在所有情况下都可行的解决方案。

I recommend you to change your data structure and add an integer next to your entities. 我建议您更改数据结构,并在实体旁边添加一个整数 The integer is called ID or Key which shows the difference between cat with ID = 3 and cat with ID = 7. so you will never get confused about which cat you are looking for. 该整数称为IDKey ,它显示ID = 3的cat和ID = 7的cat之间的差异,因此您永远不会对要查找的cat感到困惑。

The best structure for the new structure is called Dictionary . 新结构的最佳结构称为Dictionary

I changed your code below, which results cat and hamster : 我在下面更改了您的代码,结果是仓鼠

        int incrementalID = 0;
        Dictionary<int, string> list1 = new Dictionary<int, string>();
        Dictionary<int, string> list2 = new Dictionary<int, string>();

        list1.Add(incrementalID++, "dog");    //ID = 0
        list1.Add(incrementalID++, "cat");     //ID = 1
        list1.Add(incrementalID++, "fish");    //ID = 2
        list1.Add(incrementalID++, "cat");     //ID = 3
        list1.Add(incrementalID++, "cat");     //ID = 4
        list1.Add(incrementalID++, "mouse");   //ID = 5

        list2 = new Dictionary<int, string>(list1);
        list2.Remove(0);
        list2.Remove(1);
        list2.Add(incrementalID++, "cat");      //ID = 6
        list2.Add(incrementalID++, "hamster");  //ID = 7;

        Console.WriteLine("List 1" + Environment.NewLine);

        foreach (string item in list1.Values)
        {
            Console.WriteLine(item);
        }

        Console.WriteLine(Environment.NewLine + "List 2" + Environment.NewLine);

        foreach (string item in list2.Values)
        {
            Console.WriteLine(item);
        }

        var newItems = list2.Except(list1);

        Console.WriteLine(Environment.NewLine + "New Items" + Environment.NewLine);

        foreach (KeyValuePair<int, string> item in newItems)
        {
            Console.WriteLine(item.Value);
        }

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

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM