# Strange form for function calling

**URL:** <https://discuss.ocaml.org/t/strange-form-for-function-calling/938>\
**Category:** Learning\
**Created:** [October 9, 2017, 3:00pm UTC](https://discuss.ocaml.org/t/strange-form-for-function-calling/938 "2017-10-09T15:00:26Z")\
**Posts on this page:** 12\
**Page:** 1

<div class="post-metadata">

**Author:** ![Uno](https://avatars.discourse-cdn.com/v4/letter/u/59ef9b/32.png) [@Uno](https://discuss.ocaml.org/u/Uno)\
**Post date:** [October 9, 2017, 3:00pm UTC](https://discuss.ocaml.org/t/strange-form-for-function-calling/938/1 "2017-10-09T15:00:26Z")

</div>

While learning more about lwt I came across this function calling syntax. I’ve tried everything to find more about it, with no luck so far. The form I’m talking about basically is.

```
Modulex.(Whathe x).methodfoo "omg"

```

like seen in an Lwt example from [https://github.com/ocsigen/lwt](https://github.com/ocsigen/lwt)

```
let google = Lwt_unix.((List.hd addresses).ai_addr) in

```

This irritates me to no end! Because this would mean we have some compile time evaluation going on. And cannot be.

Please help :-).

Thanks  
uno

---

<div class="post-metadata">

**Author:** ![reynir](https://sea2.discourse-cdn.com/flex020/user_avatar/discuss.ocaml.org/reynir/32/6496_2.png) [@reynir](https://discuss.ocaml.org/u/reynir)\
**Post date:** [October 9, 2017, 3:12pm UTC](https://discuss.ocaml.org/t/strange-form-for-function-calling/938/2 "2017-10-09T15:12:53Z")

</div>

The function call syntax is the same. What you’re stumbling on is probably the [local open](http://caml.inria.fr/pub/docs/manual-ocaml/extn.html#sec224) syntax.

So, `let google = Lwt_unix.((List.hd addresses).ai_addr) in` is equivalent to `let google = let open Lwt_unix in (List.hd addresses).ai_addr in` which itself is equivalent to `let google = (List.hd addresses).Lwt_unix.ai_addr in` (assuming `addresses` comes from somewhere other than `Lwt_unix`).

---

<div class="post-metadata">

**Author:** ![Uno](https://avatars.discourse-cdn.com/v4/letter/u/59ef9b/32.png) [@Uno](https://discuss.ocaml.org/u/Uno)\
**Post date:** [October 9, 2017, 3:31pm UTC](https://discuss.ocaml.org/t/strange-form-for-function-calling/938/3 "2017-10-09T15:31:37Z")

</div>

whoa that was fast. Thanks a lot. I’m glad to be able to put name on it. Never heard of ‘local open’ althouth I was sure to read every book abou Ocaml. I must have missed something.

---

<div class="post-metadata">

**Author:** ![Uno](https://avatars.discourse-cdn.com/v4/letter/u/59ef9b/32.png) [@Uno](https://discuss.ocaml.org/u/Uno)\
**Post date:** [October 9, 2017, 3:41pm UTC](https://discuss.ocaml.org/t/strange-form-for-function-calling/938/4 "2017-10-09T15:41:16Z")

</div>

Ok, now that I’m actually try to write this in a more “traditional” manner (without local open), I’m still confused

You say

```
 let google = let open Lwt_unix in (List.hd addresses).ai_addr

```

is equivalent to

```
 let google = (List.hd addresses).Lwt_unix.ai_addr in

```

But how can I write this without this (func “foo”).meth syntax?

Sorry, I still don’t get it

---

<div class="post-metadata">

**Author:** ![ttamttam](https://sea2.discourse-cdn.com/flex020/user_avatar/discuss.ocaml.org/ttamttam/32/132_2.png) [@ttamttam](https://discuss.ocaml.org/u/ttamttam)\
**Post date:** [October 9, 2017, 4:03pm UTC](https://discuss.ocaml.org/t/strange-form-for-function-calling/938/5 "2017-10-09T16:03:15Z")

</div>

Not sure to understand the question.

Is the following way to write it more understandable to you?

```ocaml
let google =
  let first_address = List.hd addresses in
  first_address.Lwt_unix.ai_addr in
  ...

```

Salutations

---

<div class="post-metadata">

**Author:** ![reynir](https://sea2.discourse-cdn.com/flex020/user_avatar/discuss.ocaml.org/reynir/32/6496_2.png) [@reynir](https://discuss.ocaml.org/u/reynir)\
**Post date:** [October 9, 2017, 4:05pm UTC](https://discuss.ocaml.org/t/strange-form-for-function-calling/938/6 "2017-10-09T16:05:24Z")

</div>

`List.hd addresses` returns a record of type `Lwt_unix.addr_info`. That record has a field `Lwt_unix.ai_addr`. You could first name the result of `List.hd addresses`:

```
let google = let open Lwt_unix in let address = List.hd addresses in address.ai_addr in
```

---

<div class="post-metadata">

**Author:** ![Uno](https://avatars.discourse-cdn.com/v4/letter/u/59ef9b/32.png) [@Uno](https://discuss.ocaml.org/u/Uno)\
**Post date:** [October 9, 2017, 4:21pm UTC](https://discuss.ocaml.org/t/strange-form-for-function-calling/938/7 "2017-10-09T16:21:32Z")

</div>

Thanks alot this goes in the right direction.

But I’m sorry to say I’m still confused about this part:  
first\_address.Lwt\_unix.ai\_addr

For me it looks like Lwt\_unix.ai\_addr is called upon an expression that is evaluated on runtime.

Sorry for asking this stupid questions.

---

<div class="post-metadata">

**Author:** ![ttamttam](https://sea2.discourse-cdn.com/flex020/user_avatar/discuss.ocaml.org/ttamttam/32/132_2.png) [@ttamttam](https://discuss.ocaml.org/u/ttamttam)\
**Post date:** [October 9, 2017, 6:08pm UTC](https://discuss.ocaml.org/t/strange-form-for-function-calling/938/8 "2017-10-09T18:08:40Z")

</div>

Suppose you want to access field ´f´ of record ´r´.

If the type of ´r´ is known (ie if the module ´M´ where ´r´ type was  
defined is opened) you can write ´r.f´. But if ´M´ is not opened, you have  
to help the compiler by prepending the module in front of the field name:  
´r.M.f´.

And this can become more complexe if f type is a record defined in module  
M2. Say that you now want to access the f2 field of ´r.M.f´:

´´´ocaml  
let rf = r.M.f in  
let rff2 = rf.M2.f2  
´´´

or directly:  
´´´ocaml  
let rff2 = r.M.f.M2.f2  
´´´

Salutations

---

<div class="post-metadata">

**Author:** ![antron](https://sea2.discourse-cdn.com/flex020/user_avatar/discuss.ocaml.org/antron/32/62_2.png) [@antron](https://discuss.ocaml.org/u/antron)\
**Post date:** [October 9, 2017, 8:57pm UTC](https://discuss.ocaml.org/t/strange-form-for-function-calling/938/9 "2017-10-09T20:57:10Z")

</div>

To add another perspective, the dot character is used for two different things here:

1. Opening or specifying a module.
2. Accessing a field of a record.

  

So, taking

```ocaml
Lwt_unix.((List.hd addresses).ai_addr)

```

This means

> With module `Lwt_unix` open (its identifiers visible), “interpret” `(List.hd addresses).ai_addr`.

However, the only identifier from `Lwt_unix` in that expression is the record field name `ai_addr`. So, the expression could have been

```ocaml
(List.hd addresses).Lwt_unix.ai_addr

```

This means

> Execute `List.hd addresses`. The result will be a record of some type (that we later see is from `Lwt_unix`) that has an `ai_addr` field. Then, get the value of that `ai_addr` field. The `ai_addr` field is defined in `Lwt_unix`.

I don’t believe the following is valid OCaml record syntax, but we could make this expression a bit clearer by inserting parentheses:

```ocaml
(List.hd addresses).(Lwt_unix.ai_addr)

```

The dots have these meanings:

1. The dot in `List.hd` is the module path dot. It means refer to the identifier `hd` in the module `List`.
2. The dot in `Lwt_unix.ai_addr` is also the module path dot. It means refer to the identifier `ai_addr` in the module `Lwt_unix`.
3. The middle dot is the record access dot. It means “look up” field `Lwt_unix.ai_addr` in the record produced by the expression on the left of the dot.

The way you know which dot is of which kind is:

1. If the thing to the left of the dot is a module, then it’s a module path dot.
2. If the thing to the left is an expression, then it’s a record field access dot.

The module dot is easy to spot because the name to the left will be capitalized. Everything else is the record access dot.

EDIT: Actually, the dot is also used for string and array access, with syntax `e.[e]` and `e.(e)`. You detect this when you see the bracket or parenthesis (this is why one of the lines above wasn’t valid record access syntax).

---

<div class="post-metadata">

**Author:** ![antron](https://sea2.discourse-cdn.com/flex020/user_avatar/discuss.ocaml.org/antron/32/62_2.png) [@antron](https://discuss.ocaml.org/u/antron)\
**Post date:** [October 9, 2017, 8:59pm UTC](https://discuss.ocaml.org/t/strange-form-for-function-calling/938/10 "2017-10-09T20:59:32Z")

</div>

And to write this without any “magic” at all, you would do

```ocaml
let first_address = List.hd addresses in
let google = first_address.Lwt_unix.ai_addr in
(* ... *)

```

Perhaps it should be that way in the `README` 🙂

EDIT: Argh, forgot @ttamttam already showed it, thanks @ttamttam 🙂

---

<div class="post-metadata">

**Author:** ![kantian](https://avatars.discourse-cdn.com/v4/letter/k/4bbf92/32.png) [@kantian](https://discuss.ocaml.org/u/kantian)\
**Post date:** [October 9, 2017, 9:33pm UTC](https://discuss.ocaml.org/t/strange-form-for-function-calling/938/11 "2017-10-09T21:33:59Z")

</div>

To illustrate @ttamttam explanation with example in the REPL :

```ocaml
module M = struct
  type t = {f : int}
  let v = { f = 1 }
end

module M2 = struct
  type t = { g : M.t }
  let v = { g = M.v }
end;;
module M : sig type t = { f : int; } val v : t end
module M2 : sig type t = { g : M.t; } val v : t end

M2.v;;
- : M2.t = {M2.g = {M.f = 1}}

M2.v.M2.g;;
- : M.t = {M.f = 1}

M2.v.M2.g.M.f;;
- : int = 1

(* or like in the lwt example *)
M2.(v.g.M.f);;
- : int = 1

```

---

<div class="post-metadata">

**Author:** ![Uno](https://avatars.discourse-cdn.com/v4/letter/u/59ef9b/32.png) [@Uno](https://discuss.ocaml.org/u/Uno)\
**Post date:** [October 14, 2017, 2:49pm UTC](https://discuss.ocaml.org/t/strange-form-for-function-calling/938/12 "2017-10-14T14:49:00Z")

</div>

Thanks alot for your answers. A special thanks to antron for explaining the mixed example record field/Module lookup.
