2017-06-26 2 views
4

Ich versuche, eine Funktion zu schreiben, die alle Zahlen finden, die ein Vielfaches von mindestens einer Zahl in einer Liste sind, wo das Vielfache weniger als a ist bestimmte Nummer. Hier ist, was ich bisher versucht:Listenverständnis, um alle Vielfachen jeder Zahl in der Liste zu finden weniger als eine Zahl

def MultiplesUnderX(MultArray,X): 
    ''' 
    Finds all the multiples of each value in MultArray that 
    are below X. 
    MultArray: List of ints that multiples are needed of 
    X: Int that multiples will go up to 
    ''' 
    return [i if (i % x == 0 for x in MultArray) else 0 for i in range(X)] 

Zum Beispiel MultiplesUnderX ([2,3], 10) zurückkehren würde [2,3,4,6,8,9]. Ich bin ein wenig unsicher, wie man das mit der for-Schleife innerhalb des Listenverständnisses macht.

+1

Warum ist '3' nicht in der Ergebnisliste? –

+1

Weil ich nicht in 15 Stunden geschlafen habe. – greenthumbtack

+1

'(i% x == 0 für x in MultArray)' ist ein Generatorausdruck, keine "for-Schleife" innerhalb des Listenverständnisses (so etwas ist nicht möglich, da eine for-Schleife eine for-Anweisung benötigt) Es gibt ein Generatorobjekt zurück, das truthy ist. Sie wollen diesen Generator mit 'any' verwenden. –

Antwort

7

Sie können den Python jede() Funktion zu prüfen, ob mindestens eine Instanz eines Teilers in MultArray ist:

def MultiplesUnderX(MultArray,X): 

    return [i for i in range(X) if any(i % x == 0 for x in MultArray)] 
+0

Eine zusätzliche Klammer drin, aber ich liebe es! – greenthumbtack

+0

Dies gibt eine Liste mit vielen zusätzlichen' 0's drin, fällig zu dem "else 0" in deinem Verständnis. Auch in 2.7 wird der 'xrange' ein bisschen effizienter sein, um die Erstellung einer riesigen Liste im Vordergrund zu vermeiden. – foslock

+0

Edits sehen gut aus! – foslock

1

können Sie den Python verwenden integrierte Funktion any die True wenn die zurück iterable pass-in enthält beliebige Wahrheitswerte in Kombination mit einer Bedingung am Ende der Liste, die die Liste auf nur Elemente beschränkt, die den Aufruf any erfüllen.

def get_multiples_under(factors, max): 
    return [i for i in xrange(1, max) if any(i % factor == 0 for factor in factors)] 

Ihre gewünschte Ausgabe wird als solche gezeigt:

multiples = [2, 3] 
print get_multiples_under(multiples, 10) 
# [2, 3, 4, 6, 8, 9] 
0

Eine andere Version dieses Algorithmus, effizienter sein kann, wenn die Liste meist Co-Primzahl ist, die Sie gerade range(i, X, i) nur erzeugen, können Sie die Vielfache von i, dann verwenden Sie heapq.merge, um die Iteratoren so zusammenzuführen, dass der zurückgegebene Iterator sortiert wird.

Der letzte Schritt ist Duplikate zu beseitigen, wie Sie gehen:

import heapq 

def all_multiples(multi_list, max_N): 
    gens = [] 
    for fac in sorted(set(multi_list)): 
     # In Python 3 this is a generator of all multiples of "fac" less 
     # than max_N. In Python 2 use xrange 
     gens.append(range(fac, max_N, fac)) 

    # This will do a heap merge on the generators (which are already sorted) 
    o = heapq.merge(*gens) 
    last = None 
    for val in o: 
     if val != last: 
      yield val 
      last = val 


if __name__ == "__main__": 
    multi_list = [2, 4, 7] 
    print(list(all_multiples(multi_list, 12))) 
    # [2, 4, 6, 7, 8, 10] 
Verwandte Themen