Is there an algorithm to find all the common sub-sequences of items in 2 List<List<int>>, PRESERVING THE ORDER?

浪子不回头ぞ 提交于 2019-12-25 10:49:12

问题


There are 2 Lists. I have to find all the sub-sequences of integers contained in BOTH the List>, where the ORDER IS PRESERVED.

List<List<int>> listOfLists1 = new List<List<int>>();
List<int> list1 = new List<int>() { 1, 2, 3, 4, 5, 6 };
List<int> list2 = new List<int>() { 5, 7, 8 };
listOfLists1.Add(list1);
listOfLists1.Add(list2);

List<List<int>> listOfLists2 = new List<List<int>>();
List<int> list3 = new List<int>() { 5, 1, 2, 5 };
List<int> list4 = new List<int>() { 3, 4, 5, 7, 8 };
List<int> list5 = new List<int>() { 5, 6 };
listOfLists2.Add(list3);
listOfLists2.Add(list4);
listOfLists2.Add(list5);

The expected result is:

1 
2 
3 
4 
5 
6 
7 
8 
1, 2 
3, 4 
4, 5 
5, 6 
5, 7 
7, 8 
3, 4, 5 
5, 7, 8 

I have 2 questions:

  1. Is there an algorithm I am not aware of that can be employed to solve this kind of problem? (this is the main question).

  2. Are there other kinds of data structures instead of

    List of lists of type T

and

List of type T

that are more appropriate for solving this problem?

I solved it by creating all the sub-sequences of each of the Lists in the listOfLists1 and separately of each of the Lists in the listOfLists2, preserving the order of the items and then I found the ones contained in both (the common ones).

It seems that the step of creating all the sub-sequences is superfluous. There should be a more efficient way. Thank you in advance.

I am sorry but I seem to be unable to write the 2 kinds of lists legible. what I mean are: List of lists of type T and List of type T. I hope now it will be more clear.

The method I use to find all the sub-sequences is:

private static List<List<T>> FindAllSubSequencesOfConsecutiveCommonItems<T
>(T[] commonItemsArrangemet)
{
    List<List<T>> allSequencesOfConsecutiveCommonItems = new List<List<T>>();
    List<T> sequenceOfConsecutiveCommonItems = new List<T>();
    T currentCommonItem;
    for (int i = 0; i < commonItemsArrangemet.Length; i++)
        {
             currentCommonItem = commonItemsArrangemet[i];
             if (currentCommonItem != null)
             {
                 sequenceOfConsecutiveCommonItems.Add(currentCommonItem );
             {
             else
             {
                 if (sequenceOfConsecutiveCommonItems.Count > 0
                 {
                     allSequencesOfConsecutiveCommonItems.Add(sequenceOfConsecutiveCommonItems);
                     sequenceOfConsecutiveCommonItems = new List<T>();
                 }
             }
         }
     if (sequenceOfConsecutiveCommonItems.Count > 0
     {               
         allSequencesOfConsecutiveCommonItems.Add(sequenceOfConsecutiveCommonItems);
     }

      return allSequencesOfConsecutiveCommonItems;
}

The method that creates all the sub-sequences of a sequence of items is:

public static List<List<T>> CreateAllSubSequencesOfConsecutiveItemsPreservingSequentialOrder<T>(List<List<T>> allItems, int minimumSequenceLength)
{
    if (allItems == null || allItems.Count == 0 || minimumSequenceLength <= 0)
    {
        return null;
    }
    List<List<T>> sequencesOfConsecutiveItemsPreservingSequentialOrder = new List<List<T>>();
    for (int currentList = 0; currentList < allItems.Count; currentList++)
    {
        List<T> itemsInOneList = allItems[currentList];
        List<List<T>> sequencesOfConsecutiveItemsFromOneList = CreateAllSequencesOfConsecutiveItemsPreservingSequentialOrder(itemsInOneList, minimumSequenceLength);
        sequencesOfConsecutiveItemsPreservingSequentialOrder.AddRange(sequencesOfConsecutiveItemsFromOneList);
    }

    return sequencesOfConsecutiveItemsPreservingSequentialOrder;
}

public static List<List<T>> CreateAllSequencesOfConsecutiveItemsPreservingSequentialOrder<T>(List<T> itemsInOneList, int minimumSequenceLength)
{
    if (itemsInOneList == null || itemsInOneList.Count == 0 || minimumSequenceLength <= 0)
    {
         return null;
    }
    List<List<T>> sequencesOfConsecutiveItemsPreservingSequentialOrder = new List<List<T>>();
    for (int i = 0; i < itemsInOneList.Count; i++)
    {
        List<T> currentSequenceOfConsecutiveItems = new List<T>();
        int j = i;
        while (j < itemsInOneList.Count)
        {
            T currentItem = itemsInOneList[j];
            currentSequenceOfConsecutiveItems .Add(currentItem);
            if (currentSequenceOfConsecutiveItems.Count >= minimumSequenceLength)
            {
                sequencesOfConsecutiveItemsPreservingSequentialOrder.Add(currentSequenceOfConsecutiveItems);
                currentSequenceOfConsecutiveItems = new List<T>(currentSequenceOfConsecutiveItems);
            }
            j++;
        }
   }

    return sequencesOfConsecutiveItemsPreservingSequentialOrder;
}

来源:https://stackoverflow.com/questions/45137984/is-there-an-algorithm-to-find-all-the-common-sub-sequences-of-items-in-2-listli

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!