OCaml Определяемая пользователем ошибка возврата типа и функции - PullRequest
0 голосов
/ 08 ноября 2018

Я писал функцию с пользовательскими типами в OCaml, когда обнаружил сообщение об ошибке, которое не понимаю.

В настоящее время я использую интерактивный уровень OCaml, а также код Visual Studio для написания своего кода. Странно то, что когда я запускаю код в Visual Studio Code, он прекрасно компилируется, но сталкивается с ошибкой в ​​интерактивном верхнем уровне.

Код OCaml, на который я ссылаюсь, выглядит следующим образом:

type loc = int;;
type id = string;;

type value =
  | Num of int
  | Bool of bool
  | Unit
  | Record of (id -> loc)
;;

type memory = (loc * value) list;;

exception NotInMemory;;

let rec memory_lookup : (memory * loc) -> value
= fun (mem, l) ->
  match mem with
  | [] -> raise NotInMemory
  | hd :: tl -> (match hd with
                 | (x, a) -> if x = l then a else (memory_lookup (tl, l))
                )
;;

Код, который я написал, в основном является моей рудиментарной попыткой реализации / эмуляции поиска в памяти и возврата соответствующих значений.


Вот пример ввода :

memory1 = [ (1, Num 1) ; (2, Bool true) ; (3, Unit) ];;

Вот ожидаемый результат :

memory_lookup (memory1, 2);;
- : value = Bool true

Однако вот фактический вывод :

Characters: 179-180:
                 | (x, a) -> if x = l then "a" else (memory_lookup (tl, l)))
Error: This expression has type value/1076
       but an expression was expected of type value/1104

(просто для уточнения: ошибка касается символа a)


Кто-нибудь знает, что означают type value/1076 и type value/1104? Кроме того, если что-то не так с кодом, который я написал, кто-нибудь будет любезен указать на это?

Спасибо.

1 Ответ

0 голосов
/ 08 ноября 2018

Эта ошибка возникает на верхнем уровне, когда тип определяется несколько раз, а некоторые значения старого типа остаются в области видимости. Простой пример:

type t = A
let x = A;;
type t = A
let y = A;;
x = y;;

Ошибка: это выражение имеет тип t / 1012, но ожидалось выражение типа т / 1009

Числовая часть после имени типа в value/1076 является временем привязки для типа value. Это время привязки используется в качестве крайней меры для различения двух разных типов, которые имеют одинаковые имена. Таким образом

Ошибка: это выражение имеет значение типа / 1076 но ожидалось выражение типа value / 1104

означает, что значение memory1 было определено с типом value, определенным во время 1076, в то время как функция memory_lookup ожидала значения типа value, определенные позднее (то есть во время * 1021). *). Время привязки немного произвольно, поэтому его можно заменить просто value/1 и value/2 в OCaml 4.08.

...