{"id":13395223,"url":"https://github.com/arecvlohe/reasonml-cheat-sheet","last_synced_at":"2025-03-13T20:31:58.473Z","repository":{"id":92906982,"uuid":"120212536","full_name":"arecvlohe/reasonml-cheat-sheet","owner":"arecvlohe","description":"A cheat sheet for ReasonML -- WIP","archived":false,"fork":false,"pushed_at":"2019-04-09T21:59:02.000Z","size":23,"stargazers_count":181,"open_issues_count":1,"forks_count":7,"subscribers_count":3,"default_branch":"master","last_synced_at":"2025-03-05T16:19:03.070Z","etag":null,"topics":["bucklescript","cheatsheet","ocaml","reason","reasonml"],"latest_commit_sha":null,"homepage":"","language":null,"has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/arecvlohe.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null}},"created_at":"2018-02-04T18:46:31.000Z","updated_at":"2024-11-05T00:31:41.000Z","dependencies_parsed_at":"2023-04-25T17:01:21.114Z","dependency_job_id":null,"html_url":"https://github.com/arecvlohe/reasonml-cheat-sheet","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/arecvlohe%2Freasonml-cheat-sheet","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/arecvlohe%2Freasonml-cheat-sheet/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/arecvlohe%2Freasonml-cheat-sheet/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/arecvlohe%2Freasonml-cheat-sheet/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/arecvlohe","download_url":"https://codeload.github.com/arecvlohe/reasonml-cheat-sheet/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":243478342,"owners_count":20297238,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["bucklescript","cheatsheet","ocaml","reason","reasonml"],"created_at":"2024-07-30T17:01:46.712Z","updated_at":"2025-03-13T20:31:58.175Z","avatar_url":"https://github.com/arecvlohe.png","language":null,"funding_links":[],"categories":["Others"],"sub_categories":[],"readme":"# ReasonML Cheat Sheet\n\nReasonML is a functional, strongly typed, programming language. It looks like JavaScript and compiles to JavaScript/Node as well as other languages. It is a dialect of OCaml and is compiled using BuckleScript. Therefore, you can use OCaml and BuckleScript APIs when using Reason.\n\n## Try it Out\n\nIf you want a more interactive example of ReasonML's language features, check out this link to the ReasonML REPL on their homepage: 👉 [Click here](http://bit.ly/reason-by-example) 👈. \n\n## Comments\n\n```reason\n/* This is a comment whether single or multi-line */\n```\n\n## Types\n\n1. Types are inferred. This means you don't have to declare types but you can if you want.\n1. Type coverage is 100%. Because types are inferred it means coverage is everywhere.\n1. Type system is sound. Compile and forget.\n\nTypes: `list`, `array`, `string`, `char`, `bool`, `int`, `float`, `unit`, `option`, etc.\n\n## Generics\n\nGenerics are created by putting a `'` in front of an arbitrary variable name. However, it is most common to see single letters used.\n\n```reason\nlet length: array('a) =\u003e int;\n```\n\nGenerics allow you to use a function in a more _generic_ way. In the case of `length`, it's a function which takes an array of any type, `'a`, and returns an `int`. In this instance, `'a` can be a `string`, an `int`, or a `record`. What it enforces is that the `array` contains only that type. It can either be `array(int)` or `array(string)` but not both.\n\n## Phantom Types\n\n*\"A phantom type is a parametrised type whose parameters do not all appear on the right-hand side of its definition...\"* - [Haskell Wiki, PhantomType](https://wiki.haskell.org/Phantom_type)\n\n```reason\ntype formData('a) = string;\n```\n\nHere `formData` is a phantom type as the `'a` parameter only appears on the left side.\n\n### References\n\n- [Phantom Types in ReasonML](https://sketch.sh/s/nerP3hkOxX6sMVvVUtBIbs/) by Ali Sharif\n- [Phantom Types in ReasonML](https://medium.com/reasontraining/phantom-types-in-reasonml-1a4cfc18d999) by Kennet Postigo\n\n## Abstract Types\n\nAn abstract type is a type without a concrete definition.\n\n```reason\nmodule type Person = {\n  type details;\n  \n  let person: details;\n  let make: unit =\u003e details;\n  let greet: details =\u003e string;\n} \n```\n\nFrom the example above, the module declares the `details` type but leaves it to the module to define its implementation.\n\n```reason\nmodule Person: Person = {\n  type details = { name: string, age: int };\n  \n  let person = { name: \"Adam\", age: 31};\n  let make = () =\u003e person;\n  let greet = (details) =\u003e \"Hello. My name is \" ++ details.name ++ \" and I am \" ++ string_of_int(details.age) ++ \" years old.\";\n}\n\nlet adam = Person.make();\nlet greet = Person.greet(adam);\n```\n\n### References\n\n- [Abstract Types - Ocaml Documentation](https://ocaml.org/learn/tutorials/modules.html#Abstract-types)\n\n## List\n\nLists are created with square brackets:\n\n```reason\nlet list: list(int) = [1, 2]\n```\n\n### Spread\n\n```reason\nlet list1 = [1, 2, 3];\nlet list2 = [0, ...list1];\n\nJs.log(list2); /* [0, 1, 2, 3] */\n```\n\n_\\* Can only use the spread operator once within a list_\n\n### Rest\n\n```reason\nlet list: list(int) = [1, 2, 3, 4];\n\nlet pm = (list): string =\u003e {\n  switch(list) {\n    | [] =\u003e \"Empty\"\n    | [head, ...tail] =\u003e {j|I only want $head|j}\n  }\n};\n\nJs.log(pm(list)); /* I only want 1 */\n```\n\n## Array\n\nArrays are created with square brackets and pipes:\n\n```reason\nlet arr: array(string) = [|\"a\", \"b\"|]\n```\n\n## String\n\nStrings are created with double quotes:\n\n```reason\nlet str: string = \"Yeah, to you it's Thanksgiving; to me it's Thursday\"\n```\n\nStrings are concatenated with double plus signs:\n\n```reason\nlet stringConcat: string = \"Yo Adrian, \" ++ \"I did it!\"\n```\n\nString interpolation comes with help from BuckleScript:\n\n```reason\nlet rocky: string = \"Rocky\"\nlet mickey: string = \"Mickey\"\n\nlet scene: string = {j|$mickey makes $rocky chase chickens to get in shape.|j}\n```\n\n## Char\n\nCharacters are created using single quotes:\n\n```reason\nlet char: char = 'a';\n\nJs.log(char); /* 97 */\n```\n\n## Functions\n\n### Named\n\n```reason\nlet someFunction = () =\u003e \"someFunction\";\n```\n\n### Anonymous\n\n```reason\nlet someFunction = () =\u003e {\n  () =\u003e {\n    \"someAnonFunction\"\n  }\n};\n\nJs.log(someFunction()()); /* \"someAnonFunction\" */\n```\n\n### Labeled Arguments\n\n```reason\nlet labeledArgs = (~arg1, ~arg2) =\u003e {\n  arg1 ++ arg2\n};\n\nJs.log(labeledArgs(~arg1=\"Some \", ~arg2=\"labeled args.\")); /* \"Some labeled args.\" */\n```\n\n### Labeled As\n\n```reason\nlet labeledArgs = (~arg1 as one, ~arg2 as two) =\u003e {\n  one ++ two\n};\n\nJs.log(labeledArgs(~arg1=\"Some \", ~arg2=\"labeled args.\")); /* \"Some labeled args.\" */\n```\n\n### Default and Optional Arguments\n\n```reason\nlet labeledArgs = (~arg1=\"Some \", ~arg2=?, ()) =\u003e\n  switch (arg2) {\n  | Some(arg) =\u003e arg1 ++ arg\n  | None =\u003e arg1 ++ \"labeled args.\"\n  };\n\nlet res = labeledArgs(~arg2=?Some(\"labeled args\"), ());\n\nJs.log(res); /* Some labeled args. */\n```\n\n### Partial Application\n\n```reason\nlet labeledArgs = (~arg1 as one, ~arg2 as two) =\u003e {\n  one ++ two\n};\n\nlet firstArg = labeledArgs(~arg1=\"Some \");\n\nlet secondArg = firstArg(~arg2=\"labeled args.\");\n\nJs.log(secondArg); /* \"Some labeled args.\" */\n```\n\n_\\* Doesn't matter which order you pass the labeled argument_\n\n## Destructuring\n\n### List\n\n```reason\nlet [a, b]: list(int) = [1, 2];\n```\n\n### Array\n\n```reason\nlet [|a, b|]: array(int) = [|1 , 2|];\n```\n\n### Tuple\n\n```reason\nlet (a, b): (int, int) = (1, 2);\n```\n\n## Pattern Matching\n\nUse the `switch` to pattern match against values:\n\n```reason\nswitch (value) {\n  | 1 =\u003e \"one\"\n  | _ =\u003e \"Everything else\"\n};\n```\n\n### Literal\n\n```reason\nswitch (1) {\n  | 1 =\u003e \"one\"\n  | _ =\u003e \"Everything else\"\n};\n```\n\n### Option\n\n```reason\nswitch (option) {\n  | Some(option) =\u003e option\n  | None =\u003e None\n};\n```\n\n### Destructuring\n\n```reason\nlet arr: array(int) = [|1, 2, 3|];\n\nlet matchArr: array(int) =\u003e int = arr =\u003e {\n  switch (arr) {\n    | [|a, b, _|] =\u003e a + b\n    | [|a, b|] =\u003e a\n    | [|a|] =\u003e 0\n    | [||] =\u003e -1\n    | _ =\u003e 0\n  };\n};\n\nJs.log(matchArr(arr)); /* 3 */\n```\n\n### Guards\n\n```reason\nlet arr = [|1, 2, 3|];\n\nlet matchArr: array(int) =\u003e int = (arr) =\u003e\n  switch arr {\n  | [|a, b, _|] when a \u003c 2 =\u003e a + b\n  | [|a, _, _|] when a \u003e 2 =\u003e a\n  | [|a|] =\u003e 0\n  | [||] =\u003e (-1)\n  | _ =\u003e 0\n  };\n\nJs.log(matchArr(arr)); /* 3 */\n```\n\n## Types\n\n### Literal\n\n#### Record\n\n```reason\ntype person = {\n  firstName: string,\n  lastName: string\n};\n\nlet listOfPerson: list(person) = [{ firstName: \"Rocky\", lastName: \"Balboa\" }];\n```\n\n#### Closed Object\n\n```reason\ntype obj = {\n  .\n  color: string,\n};\n\nlet car: obj = {\n  pub color = \"Red\"\n};\n\nJs.log(car#color); /* \"Red\" */\n```\n\n_\\* Objects in Reason are like constructors in JS_\n\n#### Open Object\n\n```reason\ntype obj('a) = {\n  ..\n  color: string,\n} as 'a;\n\nlet car: obj({. color: string, isRed: unit =\u003e bool }) = {\n  pub color = \"Red\";\n  pub isRed = () =\u003e this#getColor() == \"Red\";\n  pri getColor = () =\u003e this#color;\n};\n\nJs.log(car#isRed()); /* true */\n```\n\n#### JavaScript Object\n```reason\ntype person = {\n .\n \"name\": string,\n [@bs.meth] \"greet\": unit =\u003e unit,\n};\n\nlet printPerson = (p:person) =\u003e {\n  Js.log(p##name);\n  p##greet();\n}\n```\n\n#### Tuple\n\n```reason\ntype message: (int, string) = (200, \"Success\");\n```\n\n### Tagged Union\n\n```reason\ntype person =\n  | Rocky\n  | Mickey\n  | Adrian;\n\nlet matchPerson: person =\u003e string = (who: person) =\u003e\n  switch who {\n  | Rocky =\u003e \"Rocky\"\n  | Mickey =\u003e \"Mickey\"\n  | Adrian =\u003e \"Adrian\"\n  };\n\nJs.log(matchPerson(Rocky)); /* \"Rocky\" */\n```\n\n## Operators\n\n| Symbol | Meaning                             |\n| ------ | ----------------------------------- |\n| +      | integer addition                    |\n| +.     | float addition                      |\n| -      | integer subtraction                 |\n| -.     | float subtraction                   |\n| \\*     | integer multiplication              |\n| \\*.    | float mulitplication                |\n| /      | integer division                    |\n| /.     | float division                      |\n| \\*\\*   | exponentation                       |\n| \\|\u003e    | pipe / reverse application operator |\n| @@     | application operator                |\n| ~+     | unary addition integer              |\n| ~+.    | unary addition float                |\n| ~-     | unary negation integer              |\n| ~-.    | unary negation float                |\n| ++     | string concatenation                |\n| @      | list concatenation                  |\n| -\u003e     | pipe first                          |\n\n## Helpful BuckleScript/OCaml Functions\n\n| Function                 | Meaning                                    |\n| ------------------------ | ------------------------------------------ |\n| Js.log                   | Logs value to console                      |\n| Js.Float.isNaN           | Checks to see if value is `NaN`            |\n| string_of_int            | Convert integer into string                |\n| string_of_float          | Convert float to string                    |\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Farecvlohe%2Freasonml-cheat-sheet","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Farecvlohe%2Freasonml-cheat-sheet","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Farecvlohe%2Freasonml-cheat-sheet/lists"}