Du overcomplicating diese ein wenig, und es ist unklar, was die Zwecke der f
und getlast
könnte sein, wie Sie sie nie (und die „Definition“ von f
ist ein Syntaxfehler) verwendet wird.
Wenn Sie Ihre getlast
außerhalb dieser Funktion testen (dies ist in der Regel eine gute Idee) werden Sie feststellen, dass getlast []
ist SOME []
und getlast [1,2,3]
ist SOME [1,2,3]
; getlast y
ist SOME y
egal was y
Sie gehen zu ihm.
Auch das Ergebnis List.filter func L
ist ein 'a list
, kein 'a option
, so ist es nicht sehr nützlich, da die Definition von last
.
Eine Möglichkeit, ein solches Element in der Liste zu finden xs
wird mit expliziten Rekursion:
- Wenn
xs
leer ist, ist das Ergebnis NONE
.
- Wenn
xs
nicht leer ist, zuerst sehen, ob es ein "letztes Element" im Schwanz von xs
gibt.
Wenn es ist, das ist die Antwort.
Wenn nicht, dann
- Wenn
func
für den Kopf xs
hält, das ist deine Antwort.
- Andernfalls ist das Ergebnis
NONE
.
Übersetzen dies ML, könnte es etwa so aussehen:
fun last _ [] = NONE
| last f (x::xs) = case last f xs of
NONE => if f x then SOME x else NONE
| result => result
Wenn Sie List.filter
und vermeiden manuelle Rekursion verwenden möchten, beachten Sie dann, dass das letzte Element einer Liste der ist erstes Element der Rückseite dieser Liste:
fun last f xs = case List.rev (List.filter f xs) of
[] => NONE
| y::ys => SOME y