Haskell-Prime-Test

8

Ich bin neu bei Haskell, und ich versuche es ein wenig:

%Vor%

Ich habe ein paar Fragen.

  1. Warum, wenn ich versuche, die .hs zu laden, sagen WinHugs: Instanzen von (Floating Integer, RealFrac Integer) erforderlich für die Definition von isPrime ?
  2. Wenn der Interpreter ein Element in der richtigen Menge findet, stoppt es sofort oder berechnet alle Mengen? Ich denke du weißt was ich meine.

Tut mir leid wegen meinem Englisch.

    
hsknew 27.12.2010, 20:01
quelle

5 Antworten

17

1) Das Problem ist, dass sqrt den Typ (Floating a) => a -> a hat, aber Sie versuchen, eine Ganzzahl als Argument zu verwenden. Sie müssen also Ihre Integer zuerst in ein Floating, z. indem Sie sqrt (fromIntegral x)

schreiben

2) Ich sehe keinen Grund, warum == nicht faul sein sollte, aber zum Testen auf eine leere Sammlung können Sie die Funktion null verwenden (was definitiv faul ist, da sie auf unendlichen Listen funktioniert):

%Vor%

Aber um eine idiomatische Lösung zu erhalten, sollten Sie das Problem in kleinere Teilprobleme aufteilen. Zuerst benötigen wir eine Liste aller Elemente y mit y * y & lt; = x:

%Vor%

Dann brauchen wir nur die Elemente, die x teilen:

%Vor%

Dann müssen wir prüfen, ob diese Liste leer ist:

%Vor%

Und wenn Ihnen das lispy erscheint, ersetzen Sie einige der Parens durch $

%Vor%

Für zusätzliche Klarheit können Sie die Lambdas "outsourcen":

%Vor%

Sie können es fast "menschenlesbar" machen, indem Sie null $ filter durch nicht $ any ersetzen:

%Vor%     
Landei 27.12.2010, 20:15
quelle
7
  1. Weil sqrt den Typ Floating a => a -> a hat. Dies bedeutet, dass die Eingabe ein Floating -Typ sein muss und die Ausgabe vom selben Typ ist. Mit anderen Worten, x muss ein Floating -Typ sein. Sie haben jedoch x vom Typ Integer angegeben, was kein Floating -Typ ist. Außerdem benötigt floor einen RealFrac Typ, also muss auch x das sein.

    Die Fehlermeldung weist darauf hin, dass Sie das beheben, indem Sie Integer a Floating type angeben (indem Sie eine Instanz Floating Integer definieren (und dasselbe für RealFrac ).

    Natürlich ist das in diesem Fall nicht der richtige Ansatz. Stattdessen sollten Sie fromIntegral verwenden, um x in ein Real zu konvertieren (was eine Instanz von Floating und RealFrac ist), und dann an sqrt .

  2. Ja. Sobald == sieht, dass der rechte Operand mindestens ein Element hat, weiß es, dass es nicht gleich [] ist und gibt daher False zurück.

    Das heißt, null ist eine idiomatische Methode, um zu überprüfen, ob eine Liste leer ist als [] == .

sepp2k 27.12.2010 20:12
quelle
1

Was den zweiten Punkt betrifft, so stoppt er zum Beispiel:

%Vor%

Gibt False

zurück     
aromero 27.12.2010 20:12
quelle
1

Die Lösung von Landei ist großartig, aber wenn Sie eine effizientere Implementierung wünschen, haben wir (dank BMeph):

%Vor%

Die "Effizienz" kommt von der Verwendung konstanter Primzahlen. Es verbessert die Suche auf zwei Arten:

  1. Die Haskell-Laufzeit konnte die Ergebnisse zwischenspeichern, damit nachfolgende Aufrufe nicht ausgewertet werden
  2. Es eliminiert eine Reihe von Zahlen nach Logik Beachten Sie, dass der Wert sieve einfach eine rekursive Tabelle ist, in der der Kopf von Die Liste ist prime und fügt sie hinzu. Für den Rest der Listen, wenn es keine gibt anderen Wert bereits in der Liste, die die Zahl dann seine Primzahl zusammensetzt possible ist eine Liste aller möglichen Primzahlen, da alle möglichen Primzahlen in der Form 6 * k-1 oder 6 * k-1 außer 2 und 3 Die gleiche Regel wird auch für shortCircuit angewendet, um schnell aus den Berechnungen herauszukommen

Fußnote von D.F. ¹ Es ist immer noch eine schrecklich ineffiziente Art, Primzahlen zu finden. Verwenden Sie keine Probenteilung, wenn Sie Primzahlen größer als ein paar Tausend benötigen, verwenden Sie stattdessen ein Sieb. Es gibt mehrere weit mehr effizient Implementierungen auf hackage .

    
langerra.com 31.12.2010 22:09
quelle
-2
  1. Ich denke, WinHugs muss ein Modul für Integer und etc importieren ... Try Int
  2. Der Interpreter berechnet nichts, bis Sie z. isPrime 32 , dann wird es den Ausdruck faul berechnen.

PS Ihre isPrime-Implementierung ist nicht die beste Implementierung!

    
langerra.com 27.12.2010 20:12
quelle