2017-02-26 1 views
0

ML 기능은ML 지역 enviornment

내 현재의 기능과 같습니다 이 :

fun last func nil = NONE 
| last func L = 
    let val f = 
     fun getlast(x) = SOME x 
     | getlast(x::xs) = getlast xs 
    in List.filter func L 
    end; 

아무도 내 코드를 디버깅하는 데 도움이 될 수 있으며 ML의 로컬 환경을 이해하는 데 도움이 될 수 있습니까?

답변

1

이 조금과 복잡함을하고, 그것을 당신이 결코 (구문 오류 및 f의 "정의"한다)를 사용하지 않는 것으로 fgetlast의 목적이 될 수 있는지 불분명하다.

당신은 당신이 getlast []SOME []getlast [1,2,3]SOME [1,2,3]입니다 것을 알 수 있습니다이 기능의 당신의 getlast 외부 (이것은 일반적으로 좋은 생각입니다) 테스트 경우; getlast yy에 상관없이 SOME y입니다.

또한, List.filter func L의 결과는 'a list 아닌 'a option, 그래서 그것은 last의 정의로서 매우 유용 아니다. 목록 xs 이러한 요소를 찾는

한 가지 방법은 명시 적으로 재귀를 사용하고 있습니다 :

  • 경우 xs가 비어 결과는 NONE입니다.
  • xs이 비어 있지 않은 경우 먼저 xs의 꼬리에 "마지막 요소"가 있는지 확인하십시오.
    그게 있다면 대답입니다.
    funcxs의 머리를 보유하고 다음
    • 경우에, 그것은 당신의 대답하지가됩니다.
    • 그렇지 않으면 결과는 NONE입니다. ML이 번역

,이 같은 것을 볼 수 있습니다

fun last _ [] = NONE 
    | last f (x::xs) = case last f xs of 
         NONE => if f x then SOME x else NONE 
         | result => result 

당신이 List.filter를 사용하고 수동 재귀를 피하려면, 다음리스트의 마지막 요소가 있음에 유의 그 목록의 역의 첫 번째 요소 :

fun last f xs = case List.rev (List.filter f xs) of 
        [] => NONE 
        | y::ys => SOME y