Congratulations on a deceptively difficult question. I think this will work, but I wonβt be shocked if I missed the corner case, especially with repeating elements. Revised version inspired by Hgu Nguyen recursive solution:
def sublist(a, b): index_a = 0 index_b = 0 len_a = len(a) len_b = len(b) while index_a < len_a and index_b < len_b: if a[index_a] == b[index_b]: index_a += 1 index_b += 1 else: index_b += 1 return index_a == len_a
Some rough profiling:
On lists requiring passing most or most of b , my algorithm suffers:
a = [1, 3, 999999] b = list(range(1000000))
On my PC, the Huu Nguyen or Hetman algorithm takes about 10 seconds to complete 100 iterations of the check. My algorithm takes 20 seconds.
Given earlier success, the Huu algorithm is far behind:
a = [1, 3, 5]
The hetman algorithm or mine can complete 100 thousand checks per second - the hetman in 0.13 seconds on my PC, mine in 0.19 seconds. Huu takes 16 seconds to complete a 1k check. I am frankly struck by this difference - recursion can be slow if you do not optimize the compiler, I know, but it is 4 orders of magnitude worse than I expected.
Given the list of crashes a , performance returns to what I saw when you need to crawl the entire second list - itβs understandable, since there is no way to find out that at the end there will not be a sequence that matches an otherwise unsupported list.
a = [3, 1, 5]
Again, about 10 seconds for Huu Nguyen or Getman's algorithm for 100 tests, 20 for mine.
Longer ordered lists support the pattern I saw for early success. EG:
a = range(0, 1000, 20)
With the Getman algorithm, which took 10.99 seconds to complete 100k tests, while mine took 24.08. Huu took 28.88 to complete 100 tests.
This is admittedly not a complete range of tests that you could perform, but in all cases the Getman algorithm performed the best results.