Seite 1 von 1

Hilfe, mein code funktioniert nicht!

Verfasst: Dienstag 26. Januar 2021, 16:43
von W4LL3
Meine Aufgabe ist es einen Code zu schreiben der die primzahlen bis zu einer bestimmten zahl in einer liste ausgibt. Hierzu habe ich folgenden code geschrieben..

def primes(n: int) -> list:
liste = []
primes = []
if n >= 2:
primes.append(2)
for i in range(3, n+1):
for p in primes:
if i % p == 0:
liste.append(p)
if len(liste) == 0:
primes.append(i)

return primes
else:
return primes

aus irgend einem grund gibt er mir als lösung immer nur [2,3], kann irgend jemand helfen? :)

Re: Hilfe, mein code funktioniert nicht!

Verfasst: Dienstag 26. Januar 2021, 18:52
von darktrym
Nur so als Hilfestellung, wieso füllst du eine Liste wenn bereits ein Element belegt das i nicht prim ist?

Re: Hilfe, mein code funktioniert nicht!

Verfasst: Dienstag 26. Januar 2021, 20:16
von bb1898
Es ist ausgesprochen schwer, herauszufinden, was Dein Code eigentlich tut, weil die Einrückungen fehlen. Code-Beispiele in diesem Forum gehören in Code-Tags ("Vollständiger Editor und Vorschau" gibt Zugang dazu). Ich rate jetzt mal, was Du gemeint hast:

Code: Alles auswählen

def primes(n: int) -> list:
    liste = []
    primes = []
    if n >= 2:
        primes.append(2)
        for i in range(3, n+1):
            for p in primes:
                if i % p == 0:
                    liste.append(p)
            if len(liste) == 0:
                primes.append(i)
        return primes
    else:
        return primes
Dazu: als erstes hat darktrym natürlich völlig recht, die Liste "liste" (schlechter Name, wenn schon, dann wäre "faktoren" besser) ist überflüssig. Du könntest den Durchgang durch die Primzahl-Liste entweder abbrechen, so bald zum ersten Mal "i % p == 0" wahr ist (dann ist i zusammengesetzt) oder so bald p > i/2 ist (dann ist i Primzahl, denn größer kann ein echter Teiler von i nicht sein). Je nachdem hängst Du i an primes an oder nicht.

Und zweitens wirst Du mit diesem Algorithmus nur für recht mäßige n Freude haben. Spätestens wenn n groß wird und das Ganze schnell gehen soll: "Sieb des Eratosthenes" anschauen. Das ist auch nicht die Spitze der Entwicklung, aber allemal besser als Probe-Divisionen.

Re: Hilfe, mein code funktioniert nicht!

Verfasst: Mittwoch 27. Januar 2021, 08:39
von Sirius3
Für die Fehlersuche gib am besten für jeden for-Schleifen-Schritt per print die interessanten Variablen aus. Dann solltest Du schnell sehen, warum keine weiteren Primzahlen gefunden werden.
Wenn im if-Teil und im else-Teil der selbe Code steht, kann man ihn einmal danach schreiben (dann fällt der else-Zweig komplett weg):

Code: Alles auswählen

def primes(n: int) -> list:
    liste = []
    primes = []
    if n >= 2:
        primes.append(2)
        for i in range(3, n+1):
            for p in primes:
                if i % p == 0:
                    liste.append(p)
            if len(liste) == 0:
                primes.append(i)
    return primes

Re: Hilfe, mein code funktioniert nicht!

Verfasst: Mittwoch 27. Januar 2021, 09:48
von snafu
So ein paar Annahmen kann man auch schon ohne komplizierte Mathematik treffen. Man weiß zB dass es keine Primzahl unter 2 gibt und dass abgesehen von der 2 alle Primzahlen ungerade sind. Auch würde ich nicht den Hauptteil der Funktion in den if-Block setzen, sondern den Test umkehren und bei unter 2 früh aussteigen. Weiterhin erlaubt Python einen else-Zweig für for-Schleifen. Damit spart man sich das Zwischenspeichern in der Liste. Sähe alles in allem dann etwa so aus:

Code: Alles auswählen

def get_primes(limit: int) -> list:
    if limit < 2:
        return []
    primes = [2]
    odds = range(3, limit + 1, 2)
    for candidate in odds:
        for prime in primes:
            if candidate % prime == 0:
                break
        else:
            primes.append(candidate)
    return primes

Re: Hilfe, mein code funktioniert nicht!

Verfasst: Mittwoch 27. Januar 2021, 10:10
von Sirius3
@snafu: damit hast Du die Funktion komplett umgeschrieben, so dass der ursprüngliche Fehler nicht mehr auftritt, der Lerneffekt also nicht auftritt.
Statt einer for-Schleife mit else würde man einen Generator benutzen:

Code: Alles auswählen

def get_primes(limit: int) -> list:
    if limit < 2:
        return []
    primes = [2]
    for candidate in range(3, limit + 1, 2):
        if all(candidate % prime != 0 for prime in primes):
            primes.append(candidate)
    return primes