Creating a Record where field name is a reserved keyword

Wrote this code

type grade = {math: int; physics: int; chemistry: int}
type student = {id: string; name: string; grade: grade}
type school = {school_name: string; `class`: string; students: student list}

When I do a dune build all it says is a “syntax error” on the backtick.

File “mytypes/mytypes.ml”, line 4, characters 36-37:
4 | type school = {school_name: string; class: string; students: student list}
^
Error: Syntax error

I used ChatGPT and it said that when creating records where the field name is a reserved keyword like the word class then we should use backticks to define it.

But the compiler still doesn’t like it

As the compiler says, that is not valid syntax. Typically people change the name slightly to avoid clashing with a reserved keyword. Eg, you could use the name class_ or cls.

1 Like

So there is no way to escape it?

Well, there is the ‘raw keywords’ feature: \#class OCaml 5.2.0 released

But that is available only in OCaml 5.2.0+, is not really meant for this use case, and is a super obscure feature that will confuse everyone who reads the code.

In short, it would be advisable to stick with the typical pattern of suffixing the keyword with _ to turn it into a normal valid identifier.

2 Likes

Nice hallucination there by ChatGPT. :stuck_out_tongue:

6 Likes

Bing copilot seems to have the same hallucination.

1 Like

why not just use class_name as the variable?

1 Like

Please, bullshit not hallucinations.

There is a manual where you can easily check the accuracy of whatever syntactic bullshit or “information” LLMs are going to tell you about the OCaml language. In general if something comes out wrong out of ChatGPT it’s better to question ChatGPT’s answer than the real world…

For making identifiers clashing with reserved keywords my preference is to prime them, that would be class' in this case.

6 Likes

Or precede/follow with an underscore, viz class_ or _class

Rather not precede, because e.g. _class value binding will disable the “unused” warning.

2 Likes

I don’t think there’s a meaningful difference between adding an underscore or “escaping” the keyword. In either case, you’re still writing something that’s not class in your source code. (And since record field names only exist in source code, there’s no time where it would get “unescaped.”) You might as well just use an underscore or pick a different name.

If you prefer the way backticks look, single-quotes are valid in OCaml identifiers: type school = {class': string}.

2 Likes

As a side note, in case you need to print or to export a type record information to JSON (it is similar for TOML etc) you can still export with the actual class name with something like:

type school = { school_name: string
              ; class_name: string [@key "class"]
              ; students: student list} [@@deriving yojson { exn = true }, show]
2 Likes