2016-04-10 6 views
2

Das Folgende ist meine Fakultäts-Funktion falsch ist:Haskell: Was ist mit Fakultätsfunktion

factorial :: Integer -> Integer 
factorial n 
    | n < 0 = -1 
    | n > 0 = n * factorial (n-1) 
    | n == 0 = 1 

Ich denke, bedeckte ich alle Fälle (+ ve, -ve, 0). Wenn ich versuche, den obigen Code zu laden, erhalte ich folgende Warnungen. Warum bekomme ich Warnungen?

Antwort

1

Ich denke, der Compiler ist nicht schlau genug zu wissen, dass die Abdeckung der drei Fälle erschöpfend für den jeweiligen Typ ist. Verwenden Sie einfach das otherwise Muster in der dritten Regel anstelle von Null?

(Und nebenbei wird faktorielles in der Regel nur für positive ganze Zahlen definiert, damit ich weiß nicht, wie viel Ihre negativen Zweig korrekt ist.)

4

Diese ghc ist konservativ. Ihr Code enthält alle möglichen Werte von "n", aber ghc ist nicht schlau genug, dies zu beweisen, also warnt er Sie.

Ersetzen Sie Ihre "n < 0" durch "sonst" und setzen Sie sie am Ende. Dies ist definiert als

otherwise = True 

Das wird der Catch-All-Fall, der Ghc bequem machen wird.

+0

Das heißt, einen Fall addieren '| sonst = Fehler "Das Unmögliche ist passiert." Oder etwas in dieser Richtung. – AJFarmar

+0

Ich denke, Paul bedeutet, einen der legitimen Fälle mit einem Catch-All Case zu behandeln. Ich würde [wenn möglich, von 'Fehler' wegbleiben] (http://programmers.stackexchange.com/questions/252977/cleanest-way-to-report-errors-in-haskell). – zoul

2

Der Compiler kann nicht erkennen, dass alle Eingaben mit mindestens einem von drei Wächtern übereinstimmen.

Hier ist ein Vorschlag, zu beheben und auch einige Wiederholungen entfernen:

factorial :: Integer -> Integer 
factorial n = case compare n 0 of 
    LT -> -1 
    GT -> n * factorial (n-1) 
    EQ -> 1