Есть два места, где вы можете использовать let
в OCaml. На верхнем уровне модуля вы можете иметь это:
let pattern = expression
Модуль, по сути, представляет собой набор именованных значений, и эта форма let
является способом определения имени и его значения.
С другой стороны, есть выражение OCaml, которое выглядит так:
let pattern = expression1 in expression2
По сути, это способ определения локальных переменных для использования в expression2
.
Ваш код с ;
не работает ни в одной из этих форм. ;
используется для объединения двух выражений в одно выражение. Но let pattern = value
это не выражение. Он имеет форму объявления модуля верхнего уровня.
Причина, по которой он работает при удалении ;
, заключается в том, что у вас есть два объявления верхнего уровня. Это будет работать до тех пор, пока код появится на верхнем уровне модуля. В этом случае он определяет имена rodrigue
и diegue
как именованные значения модуля.
Другие ответы:
В последних версиях OCaml строки не являются изменяемыми. Вам нужно использовать тип bytes
, если вам нужна изменчивость. В рамках этого изменения запись string.[...] <- ...
устарела. Вы должны использовать Bytes.set
вместо.
# let mystring = "abc";;
val mystring : string = "abc"
# let mybytes = Bytes.of_string "abc";;
val mybytes : bytes = Bytes.of_string "abc"
# mystring.[0] <- 'b';;
Warning 3: deprecated: String.set
Use Bytes.set instead.
Error: This expression has type string but an expression was
expected of type bytes
# Bytes.set mybytes 0 'b';;
- : unit = ()
# mybytes;;
- : bytes = Bytes.of_string "bbc"
У OCaml на самом деле нет заявлений. В местах, где у вас есть оператор на некоторых других языках, у вас есть выражение типа unit
. Например, оператор for
в OCaml на самом деле является выражением типа unit
.
# for x = 1 to 1 do () done = ();;
- : bool = true
С этой точки зрения 4 = 4
является выражением, поскольку оно имеет тип bool
(а не unit
).
Итак, let x = 5
не является ни выражением, ни утверждением (которое является просто разновидностью выражения). Как я указывал выше, это имеет форму объявления модуля верхнего уровня. Следовательно, он может появляться только в верхней части модуля.
Напротив, let x = 5 in x + 2
- это выражение со значением 7.
Имя toplevel
- это то, что ветераны OCaml называют циклом read-eval-print OCaml. Другими словами, это имя для интерпретатора OCaml.
В моих ответах выше я использую «верхний уровень» для обозначения самого внешнего синтаксического уровня вложенности модуля. Это не то же самое, что верхний уровень (интерпретатор OCaml).