2017-09-15 80 views
8

Ten kod kompiluje dobrze w F # oraz SML:Dlaczego to wyrażenie "dopasuj" F #/OCaml?

let testmatch k = 
    match k with 
    | jqk3jtl23jtlk123 -> true 

Przetestowałem zarówno FSI i Utop. Zawsze zwraca true.

Numer jqk3jtl23jtlk123 jest całkowicie losowy, a jego typ jest interpretowany jako 'a. Nawet jeśli ograniczyć k z typów danych (np let testmatch (k: int) =) kompiluje (choć oczywiście ograniczać testmatch „s typ do int -> bool zamiast 'a -> bool

Czy ktoś mógłby wyjaśnić, co się dzieje szczególności:.?

  • dlaczego kompilator przyjąć całkowicie losowy dosłowne jqk3jtl23jtlk123?
  • dlaczego nie dostać inexhaustive ostrzeżenie meczu?
  • co jest mecz rzeczywiście robi?
+7

Nie jesteś dopasowywania wartości 'jqk3jtl23jtlk123', jesteś tworząc wartość o nazwie' jqk3jtl23jtlk123' pasujący cokolwiek 'k' jest. – Marth

+2

W tych językach zazwyczaj znajdujesz się w wyrażeniu wartości lub wyrażeniu dopasowującym do wzorca, a te dwa zachowują się w różny sposób. Dopasowywanie wzorców zachodzi po 'match ... with', after' function' oraz w dowolnych parametrach funkcji/metody. – TheQuickBrownFox

Odpowiedz

15

W tym przypadku "literalna" jqk3jtl23jtlk123 jest poprawną nazwą zmiennej, a więc opis opisany po lewej stronie -> jest taki sam, jak w przypadku napisania let jqk3jtl23jtlk123 = k. Ponieważ akceptuje ona dowolną wartość k i nie ogranicza jej typu, ponieważ powiązanie działa dla wszystkich typów, wywnioskowany typ to 'a, najbardziej ogólna wartość, jaką może reprezentować system typów.

Jeśli zmienisz literał w coś, co nie jest prawidłowym identyfikatorem, na przykład zaczynając od cyfry, nie uda się skompilować.

Jeśli owinąć dosłowne w cudzysłowie, będzie interpretowana jako wartość ciągu dosłownym, należy uzyskać inexhaustive ostrzeżenie mecz, a to ogranicza k „s typ do string.

9

To jest wzór wieloznaczny, który nazywa wszystko, co jest k równe. Jest to odpowiednik

let testmatch k = 
    let jqk3jtl23jtlk123 = k in 
    true