3 ms·
You can do this in any language, even C
by maccard 4y ago
You can do this in any language, even C
- tialaramex 4y agoC isn't very good at type correctness. In a lot of languages if I call F(some_array) it passes the array, in C it passes... A pointer to the first element in the array. C programmers, like a dog whose master kicks it when he's drink, are used to this, but it's not actually good. For this behaviour to be ergonomic you need consistent type correctness. A language which thinks 5 is true is already shaky about types, let alone one which thinks arrays are pointers.
- adrian_b 4y agoWhile I completely agree that the implicit conversions between arrays and pointers are very bad, in decades of using C and many other programming languages I have seen neither any case when 5 being true is undesirable nor any case when a distinct "Boolean" type is useful.
- samatman 4y agoI've seen plenty of cases of it being undesirable for 0 to be false, in languages which aren't C. In C, and any other language where the memory model is based on bits and bytes, it's well defined, there's no meaningful way for a value to be 'falsey', so I'd agree that a distinct boolean type doesn't do a lot. I could make a case that it lets the compiler choose the width of a boolean, but that's not necessarily good.
- Jtsummers 4y agoHaving a distinct boolean type prevents this error (fortunately detectable with linters, so pay attention to your linter output): if(n = 5) { ... } When the author probably meant: if(n == 5) { ... } In languages where the assignment statement can also be used in expressions (as it evaluates to the value being assigned) the above can create very subtle errors in a program. Having a distinct boolean means that the type system will reject that. Of course, it wouldn't reject this: if(b = true) { ... } But that's something you generally shouldn't write anyways (and, again, your linter will probably catch).
- eMSF 4y agoMany languages with distinct boolean types do not require that the condition expression in an if statement evaluates to that type, and hence do nothing to prevent that error.
- tialaramex 4y agoModern C actually has a boolean type, named _Bool (aliased bool if you ask for it explicitly) and yet sure enough despite this it figures '0', 100 and 0.1 are all truthy. Yes, what's critical here is that the only type that should be boolean true is the boolean value true, and your language is letting you down when it insists strings, or integers or some other type entirely should be "truthy" because it was easier than writing what you meant - soon or later this type laziness will bite you. I think this is more obvious in languages with pattern matching where the boolean if condition is just the world's least interesting pattern match, clearly (69, "Nice", true) doesn't match (true, true, true) as a pattern and is instead a type error.
- adrian_b 4y agoThe possibility of writing by mistake an assignment in a condition test is something strictly specific to C and derived languages and this is without doubt one of the greatest errors in the design of C. In any language that keeps the Algol notation, i.e. where "=" is a relational operator and ":=" is assignment, this kind of mistake is extremely difficult to make and easy to notice when it happens nonetheless. So the fact that a programming language can have a bad notation for equality that leads to mistakes cannot be used to justify unnecessary complications in different kinds of Boolean expressions.
- qsort 4y agoI don't disagree with what you're saying, but whatever (little) type safety C has can still be put to good use for the purposes of the article. The problem he's outlining is that you have two kinds of strings: "clean" strings and "tainted" strings, and you can only get a "clean" string from some kind of escaping function that returns "clean" strings. That's the typical problem you solve with types, and it's been true forever, even in old versions of C.
- DonaldFisk 4y agoThe idea in the article is to make wrong code look wrong, so it's even more important to make it easier for programmers to check code visually for errors in weakly typed languages such as C, where wrong code can easily get past the compiler. Even in strongly typed languages such as Haskell or Ada, it's still a good idea as it's useful self-documentation, and it also means you're less likely to get compilation errors.
- maccard 4y agoI didnt suggest passong pointers. C's type system is strong enough to let me do typedef struct { char* buf; int sz; } safe_string; typedef struct { char* buf; int sz; } unsafe_string; And differentiate between the two.