arraysocamlhashtableml

Calling OCaml functions like: 'a hash_entry list array -> string -> 'a -> unit


I am reading a book on OCaml, I am new to OCaml so I am doing the exercises and examples-though not everything compiles. In this case, my project tonight is an example of a hash table which compiles and is very interesting but I can't get it working.

let random_numbers =
  [|0x316666;   0x2d331c;   0x4de673;   0x63a91e;   0x87bee8|]
let random_length = Array.length random_numbers
type hash_info = { mutable hash_index : int; mutable hash_value : int }
let hash_char info c =
  let i = Char.code c in
  let index = (info.hash_index + i + 1) mod random_length in
info.hash_value <- (info.hash_value * 3) lxor random_numbers.(index);
info.hash_index <- index
let hash s =
  let info = { hash_index = 0; hash_value = 0 } in
  for i = 0 to String.length s - 1 do
    hash_char info s.[i]
  done;
  info.hash_value
type 'a hash_entry = { key : string; value : 'a }
type 'a hash_table = 'a hash_entry list array
let create () =
  Array.make 101 []
let add table key value =
  let index = (hash key) mod (Array.length table) in
  table.(index) <- { key = key; value = value } :: table.(index)
let rec find_entry key = function
  { key = key' ; value = value } :: _ when key' = key -> value
  | _ :: entries -> find_entry key entries
  | [] -> raise Not_found
let find table key =
    let index = (hash key) mod (Array.length table) in
    find_entry key table.(index);;

The author unfortunately will say things like 'a string -> unit will do this or that when such is not actually the case. Here for example is what I am dealing with:

utop # add = { key = "9999999" ; value = "one of these days" };;
Line 1, characters 6-55:
Error: This expression has type string hash_entry
       but an expression was expected of type
         'a hash_entry list array -> string -> 'a -> unit

I am getting frustrated with these extensive statements. What does this mean?

'a hash_entry list array -> string -> 'a -> unit

I am not asking for a definition of the parts of it, how do I use this statements to call the function? I understand that understanding the parts of this is important of course, how do these things work? A couple of days a go, for another example I was stuck on expecting type unit, what on earth is "type unit" supposed to be? Specifically, how can I generate this (knowing that it expects a key/value pair):

'a hash_entry list array -> string -> 'a -> unit

Solution

  • Here is the expression you are having trouble with:

    add = { key = "9999999" ; value = "one of these days" }
    

    This is an expression, but it's not a call to add. add is a function of 3 parameters, so a call would look like this:

    add mytable mykey myvalue
    

    Instead this expression is a comparison, i.e., it tests whether two things are equal. That's because the only operator in the expression is =, the equality comparison operator.

    Since add is a fuction, it isn't even the right type to compare against a record, which is what appears on the right side of the comparison. So that's why you're getting an error from the interpreter.

    If you want to test a call to add, it would look something more like this:

    # let table = create ();;
    val table : '_weak1 list array = ...
    # add table "mykey" "myvalue";;
    - : unit = ()
    # find table "mykey";;
    - : string = "myvalue"