2012-09-27 2 views
0

아래 코드는 단지 프로토 타입의 일종입니다. 내가 알고 싶은 것은 그것이 왜 컴파일되지 않는지입니다.ML 코드의 오류 이유

fun test(list) = 
    let 
    fun inner(list) = 
    let 
     val from = #1(hd(list)) 
     in 
     if null(tl(list)) = false then innerinner(tl(list),from) 
     else false 
     end 
    fun innerinner(list,from) = 
     if #2(hd(list)) = from then true 
     else if null(list) = false then innerinner(tl(list),from) 
     else false 
    in 
    inner(list) 
    end; 

오류 메시지는 다음과 같습니다

test.txt:7.34-7.44 Error: unbound variable or constructor: innerinner 
test.txt:3.2-9.6 Error: unresolved flex record 
(can't tell what fields there are besides #1) 
test.txt:10.2-13.13 Error: unresolved flex record 
(can't tell what fields there are besides #2) 

uncaught exception Error 
raised at: ../compiler/Toplevel/interact/evalloop.sml:66.19-66.27 
.... 

나는 ML 프로그래밍의 종류 초보자입니다. 아무도 저에게 잘못된 것을 가르쳐 줄 수 있습니까?

답변

2

여기에 꽤 많은 일들이 있습니다. 우리가 처음 보는 오류.

  1. 언 바운드 변수 또는 생성자 : SML에서

    innerinner 당신이이 선언 된 물건 전에 "사용"할 수 없다. 귀하의 경우에는 주위에 함수 선언을 스와핑하여 앞에 innerinner을 선언하면 쉽게 고칠 수 있습니다.

    예를 들어 상호 반복적 인 두 개의 함수를 선언하려는 경우에는 이것이 옵션이 아닙니다. 이 경우 키워드 and을 사용해야합니다.

  2. 해결되지 않은 플렉스 기록은

    이 좀 더 복잡하다. 그것은 형식 오류이며 튜플은 내부적으로 레코드로 표현되는 사실 과 관련이 있습니다 (나는 에 대해 읽어 보시기 바랍니다). 따라서 충분한 정보를 제공하지 않으면 타입 시스템이 불평 할 것입니다.

    나는 this QA이 그것을 아주 잘 설명한다고 생각한다. 요약하면 무한 튜플 을 가질 수 없으므로 유형 시스템에 포함 된 요소의 수를 명확하게해야합니다. 이 은 함수 선언에 명시 적으로 주석을 달아 수행 할 수 있습니다. 그러나 일반적으로 가능하면 자주 패턴 매칭을 사용해야합니다.

일반적으로 항상 튜플 선택기 (# 1, # 2, ...) 또는 목록 선택기 (hd 또는 tl)보다는 패턴 일치를 사용해야합니다. 방금 터플 셀렉터가 "좋지"않은 이유를 보았지만 목록이 비어 있는지 여부를 테스트하지 않고 목록 선택기를 사용하면 런타임 오류 (예외)가 발생합니다.

코드에 이러한 테스트 사례를 넣으면 "불어서"읽기가 지저분해질 것입니다. 그러나 패턴 매칭을 대신 사용하면 함수 정의에 멋진 명확한 사례가 생깁니다. 또한 자주 작가에게 적은 코드를 사용하는 경향이 있습니다 (제 의견으로는).

Btw를 사용하면 test 함수의 기본 정의와 같은 함수에 단일 인수를 괄호로 묶지 않아도됩니다.

모든 기능은 다음과 같이 볼 수 있었다 모든 지역 :

fun test list = 
let 
    fun innerinner ((x1, x2)::xs,from) = 
     if x1 = from then true 
     else innerinner(xs,from) 
    | innerinner ([], from) = false 

    fun inner ((x1, x2)::xs) = innerinner(xs,x1) 
    | inner [] = false 
in 
    inner(list) 
end 
+1

또는 (에서 XS) OrElse라는 innerinner에서 아마도'X1 =') 원인 –

+0

을하지만, 훨씬에 엉망하지 않으려 고 노력 원래 함수 및 내 포인트를 느슨하게 위험 :) –