2016-11-26 6 views
1

Version 3.x - will einfachste und nativer Weg wissen, die folgenden zu lösen:Entfernen Unterschied aber halte Ordnung und Duplikate in Python Listen

Beispiel Listen:

listA = [1, 2, 3, 66, 0] 
listB = [0, 0, 1, 2, 3, 66, 0, 99, 0, 3] 

Wie entferne ich die Unterschied zwischen 2 Listen, so dass eine neue Liste C dasselbe wird wie ListA mit der exakt gleichen Reihenfolge?

So das Beispiel oberhalb des listC verwenden, sollten [1, 2, 3, 66, 0]

Liste A gleich größer als Liste B und der andere Zustand sein könnte, ist, dass der Liste A wird nie in der Wiederholungs-Zahlen anders als Liste B haben, die Duplikate haben könnte.

Die Übung Charity-Verein zu lösen ich versuche:

Linday Gehirn-Test:

ein Programm schreiben, bitte, den Druck ‚Ja‘, wenn Elemente von B in A treten in der Reihenfolge, in sie erscheinen B aber nicht notwendigerweise hintereinander. Andernfalls sollte das Programm "NEIN" drucken.

Linday Bonus Test:

Bitte schreiben Sie ein Programm, das druckt ‚JA‘, wenn Elemente von B in A treten in der Reihenfolge, wie sie in B erscheinen und hintereinander.

Offensichtlich, wenn jemand Lust auf die Herausforderung hat, dann posten Sie bitte komplette Programme, um diese 2 Fragen zu lösen.

+0

Lindays Gehirntest fragt nur, ob B eine ** Unterfolge ** von A ist, oder? –

+1

Sie schreiben: * "Liste B wird nie in Wiederholungszahlen enthalten, im Gegensatz zu Liste A whist [sec] könnte Duplikate haben." *: Aber das Beispiel, das Sie geben, verstößt gegen diese Bedingung: * listB * hat in Ihrem Beispiel Duplikate. – trincot

+0

Ich habe diesen Fehler korrigiert, aber Trincot deine Lösung funktionierte für den ersten Teil danke wirklich gut Layout und einfach. Kannst du freundlicherweise die Bonus-Frage-Lösung – NoobyD

Antwort

1

Ein anderer Ansatz, der nur wenig betrügt, ist die Verwendung von Zeichenfolgen mit dem in Operator zu machen. Wenn Sie jede Liste in eine Zeichenfolge konvertieren, können Sie schnell sehen, ob A in der gleichen Reihenfolge eine Teilzeichenfolge von B ist, und fortlaufend.

def aInB(listA, listB): 
    str_a = "," + ",".join([str(c) for c in listA]) + "," 
    # ',1,2,3,66,0,' 
    str_b = "," + ",".join([str(c) for c in listB]) + "," 
    # ',0,0,1,2,3,66,0,99,0,3,' 

    return str_a in str_b 
# True 

Jetzt nur das funktioniert, wenn die Länge von A kleiner als B, sondern durch die Definition des Problems, es klingt wie das immer der Fall ist. Die zusätzlichen Kommas sind notwendig wegen des Problems, das @stefanpochmann in den Kommentaren aufgezeigt hat.

des Erste „JA“ und „NEIN“ zu drucken, ist sehr einfach:

if aInB(listA, listB): 
    print("YES") 
else: 
    print("NO") 

Für den nicht-konsekutiven Ansatz, glaube ich, würden Sie eine der iterativen Ansätze zu tun haben. Diese Lösung soll hier einfach eine alternative Denkweise über "A in B" bieten.

EDIT: Ich konnte mir nicht helfen, also hier ist ein interaktiver Ansatz, der wahrscheinlich viel zu viel ist, aber vielleicht finden Sie es leichter zu verstehen (man weiß es nie).

def aInB(listA, listB): 
    # if listA is empty, don't even bother 
    if not listA: 
     return False 

    # build a dictionary where each key is a character in listA 
    # and the values are a list containing every index where that character 
    # appears in listB 
    occurences = {c:[i for i,e in enumerate(listB) if e==c] for c in listA} 

    # now we are going to walk through listA again 
    # but this time we are going to use our `occurences` dictionary 
    # to verify that the elements appear in order 
    last_index = 0 
    for i,e in enumerate(listA): 
    # if the character `e` never appears in listB 
    # then it will have an empty list 
    # and we can return False 
    if not occurences[e]: 
     return False 

    # now the next possible index for the next character in listA 
    # must be *greater* than the index of the last character we found 
    # if no such index exists, then listA is not contained within listB 
    # if it is, we update the last seen index 
    next_possible_index = [x for x in occurences[e] if x > last_index] 
    if not next_possible_index: 
     return False 
    last_index = next_possible_index[0] 

    # if we make it out of the for loop 
    # then all is well, and listA is contained in listB 
    # but not necessarily consequtively 
    return True 
+1

Fails zum Beispiel 'aInB ([1], [11]) '. –

+0

Guter Fang. Dafür gibt es eine Lösung. – TheF1rstPancake

0
def f(l1, l2): 
    i1 = 0 
    i2 = 0 

    while i1 < len(l1) and i2 < len(l2): 
     if l1[i1] == l2[i2]: 
      i1 += 1 
      i2 += 1 
     else: 
      i2 += 1 

    if i1 == len(l1): 
     return True 
    return False 

listA = [1, 2, 3, 66, 0] 
listB = [0, 0, 1, 2, 3, 66, 0, 99, 0, 3] 

print (f(listA, listB)) 
# will print true 
+0

Ok du bist offensichtlich ein kluger Typ - wie benutze ich das im selben Programm, ohne diese Funktion zu erstellen? – NoobyD

+0

Entschuldigung, dies ist nur eine Idee, um das Problem zu lösen, das 'JA' oder 'NEIN' ausgeben soll. – Gnukos

+0

Warum möchten Sie keine Funktion erstellen? – Gnukos

Verwandte Themen