4 ms·
It looks partly like OCaml, with the "let ... in" kind of syntax. Also the "unit" word. I think in OCaml it means a function that doesn't return any value, but
by fuzztester 2y ago
It looks partly like OCaml, with the "let ... in" kind of syntax. Also the "unit" word. I think in OCaml it means a function that doesn't return any value, but why is the word unit used for that?
- chris_pie 2y agoIt's a standard practice in functional languages: https://en.wikipedia.org/wiki/Unit_type https://en.wikipedia.org/wiki/Unit_type
- fuzztester 2y agoThat sounds like those corporate types who brush off any complaints by users, by saying "that is corporate policy" :) #sorrycouldntresist But seriously, according to that link, it seems to me like the zero or empty type is more suitable. But I am not a PL or type theory expert.
- saithound 2y ago> But seriously, according to that link, it seems to me like the zero or empty type is more suitable. That's a bit different. The empty type is only suitable for functions that never return (e.g. loop infinitely, crash the program). The type checker will prevent functions that have the empty type as a return type from returning.
- akdas 2y agoTo expand on this: the "unit" here represents the number of possible values that can be returned. The confusion is probably because "empty" can mean two things: - What's inside the returned value. That may be why the parent suggested empty for the unit type. But that's now what "unit" means in the common parlance. - How many possible values can be returned. Never returning means the function has zero possible return values.
- lmm 2y agoIt's a one type, not a zero type - the function does return and it always returns the same thing. It makes this kind of function more normal and regular - you can say that functions always return 1 value, and then it means you don't have to special-case void functions (which is a problem you have to work around in e.g. C++ templating), you can do things like put the return value of the function in a variable and then use it for something since it's just a normal value (which matters if you want to write e.g. a generic compose function that runs a bunch of functions in, IDK, a database transaction or something).
- 1-more 2y agoYou've gotten some great answers but lemme add another thing: The zero type is useful for things that should not happen that you can prevent at compile time, while the unit type is nice for things that can only happen one way. In Elm (a functional language for making web UIs), you might use the unit type for a lazy view function. If and only if some condition is true, call a view function to render some stuff into your DOM tree as in the function viewIfLazy [0]. There's only one way to call that view function, so let's call it with the unit type. Now, what about using the Never type (a type with no members that can be instantiated at runtime [1]) to do accessibility? In Elm, your DOM elements have type `Html msg` where msg is a type _parameter_ for your actual message type that makes your app update itself. Usually you create that type like `type Message = UpdatedTheFooCounter Int | UpdatedTheNameInput String | ClickedTheBlahButton` something like that. Then the type on your inputs and buttons will be `Html Message` (read as "Html of Message" or even "Html parameterized by Message"). Well, it's bad a11y practice to have onclick events attached to divs and spans and things that aren't buttons, generally. So you can give your divs type `Html Never` and then if you try to attach an onclick event to them, you find that you can't at compile time, because the members of the type Message are not members of the type `Never`. tesk9/accessible-html is a package that enforces that [2] (I kind of simplified how it does that because I'm deep enough in the weeds already). [0] https://github.com/elm-community/html-extra/blob/0b8fc70752c9120b6ef997976855f3fde502de26/src/Html/Extra.elm#L65-L84 https://github.com/elm-community/html-extra/blob/0b8fc70752c... [1] https://package.elm-lang.org/packages/elm/core/latest/Basics#Never https://package.elm-lang.org/packages/elm/core/latest/Basics... also has a simpler example now that I think of it. [2] https://github.com/tesk9/accessible-html/blob/master/src/Accessibility.elm#L603-L608 https://github.com/tesk9/accessible-html/blob/master/src/Acc...
- zamalek 2y agoIt's more precise to think of unit as an empty tuple. A tuple is like an ad-hoc struct without names for the fields, so `(int, string)` is like `struct MyTuple { int a; string b; }`. An empty tuple would be `()` (which is the syntax for unit in many languages), meaning `struct MyTuple {}`. If you think about it, that's about the closest you can get to "nothing" without invoking type system handwavium (like void, which is basically "unit without the good parts but that can also mean anything"). You can do clever stuff with it, for example `HashMap<string, ()>` is practically identical to `HashSet<string>` (depending on how clever the compiler is, possibly actually identical).
- chills 2y agoI don't think it's particularly useful to think of unit as an empty tuple specifically, that is just an arbitrary but convenient definition for it. Really a unit type is just one that contains only a single value. This is a unit in the same way that 1 is a unit for the integers. With some hand waving it is an identity for product types, for example (int, ()) is the "same" (xxxmorphic yada yada) as int
- winwang 2y agoMildly disagree with your first statement. Well, I mostly agree that it's not particularly helpful for newcomers. As a 0-tuple, it becomes a specific case of a more general concept -- there is some beauty/usefulness in not having to have a "special" construct for "Unit", which is (in a sense) not just "any" unit type. It also "justifies" the syntax of `()` and notes that it is a product type, all the while fitting into the idea of the "cardinality" of `(a1, a2, ..., an)` being the product of the cardinalities of each of its type params.
- fuzztester 2y ago>you think about it, that's about the closest you can get to "nothing" Some other options could be to use None (like Python does) or Nil or Nothing itself, or even ReturnsNothing to be more explicit, or even the Pascal-style procedure keyword, instead of the function keyword, for a sub routine that returns nothing.
- fuzztester 2y agothanks, guys.
- moron4hire 2y agoThis comes up in languages where everything is an expression, nothing is a statement. Because everything is an expression that needs to be evaluated, everything has a return type. You can't have something that doesn't return literally nothing (void), you have to return an empty expression. Thus, unit. Requiring all language constructs be expressions and eliminating statements means that you avoid a lot of duplicate effort in the language design. For example, in C-like language you have if-else statements and ternary expressions. The ternary expression does "the same thing": as condition statements, but it also evaluates to a value. So in functional programming languages, you just have the one kind of conditional expression, and then maybe some syntactic sugar to morph it into more ergonomic forms.