5 ms·
Not Explicit
- scribu 9y agoWhat a useful breakdown! It seems like the narrow definition of “explicit” that the author uses is equivalent to “deterministic”. If that’s true, then “explicit” could always be replaced with a more precise alternative.
- bad_user 9y agoNo, I don’t think that’s what the author is saying, but to make it clear the definition is: “In computer science, a deterministic algorithm is an algorithm which, given a particular input, will always produce the same output, with the underlying machine always passing through the same sequence of states” In turn what the author is saying is precisely what he says, no more, no less - explicit code is code whose behavior you can understand just by reading it, with no external context, like how the runtime currently works on a particular hardware. The examples he gives are very clear as well. For example he claims to know the stack allocations that will happen just by looking at the definitions of the data types. You can’t know this on the JVM for example because the JVM does optimizations under the hood that the programmer cannot control or reason about. This doesn’t yield non-determinism. What happens is that the developer ends up programming for a higher level machine that hides some details of the underlying hardware. Explicit isn’t always better than implicit, an argument that the author also makes. Overall I find the article very compelling and I’ll be sure to use it for reference, as it’s what I also think, but with better words.
- judofyr 9y ago> In turn what the author is saying is precisely what he says, no more, no less - explicit code is code whose behavior you can understand just by reading it, with no external context, like how the runtime currently works on a particular hardware. I'm not sure where this definition is coming from. Let's look at this code: vec.len() I understand this behaviour very clearly. This will invoke the method given the following rules: - Look for `len` on the type of `vec` - If `vec` implements Deref it will look for `len` there - Look for `len` on traits that the type of `vec` implements - And so on… Yes, the behaviour is conditional, but it's still well-defined and easy to understand, although complex. "Implicit" is usually used when you want to describe situations where there are multiple interpretations, and one is chosen due to context. In Ruby: first_name + " " + last_name In this example `first_name` can either be a local variable or a method call (which can either be in the same class, an included module, or a method_missing). Here it turns out it was a method call, and we therefore call this an "implicit method call". I can rewrite: self.first_name + " " + self.last_name In this case there is a single interpretation: It can only be a method call. However, while this code is explicit on whether or not it's a method call, it's not explicit about which method is being invoked. Usually this implicitness is considered a good feature since it allows abstraction, polymorphism and so on.
- masklinn 9y agoNot really, programming languages behaviours are almost always deterministic (UB + compiler shenanigans aside). For instance the weirder corners of JS value coercions are exhaustively documented and deterministically followed by browsers, but I would argue they're not explicit, unless you're bi-classed language lawyer or have already been bitten several times, you don't "see" this (again completely deterministic) process when reading the usually innocent-looking code which ends up invoking it.
- octothorpes 9y agoIt is worrying that you have to explicitly/verbosely write article about explicitness, I thought people knew.
- wgjordan 9y agoTo the contrary, the article about _implicitness_ is the one that doesn't need to be written because people already know what it means.
- millstone 9y agoI didn't agree with this article's definition of "explicit," which feels tautological: Rust is explicit because you can figure out a lot about your program from the source of it. But as long as the source code conveys the information, it is still explicit in the narrow sense I defined above. But if the thing will happen deterministically in a manner that can be derived from the source, it is still explicit in the narrow sense that I laid out earlier. Source code conveys everything possible about your program in any language. The best notion of "explicit" is captured by the critique of "local." Here's some nice ways in which Rust is more "local" than C++: 1. Macros require bang!s instead of C++ surprise-insides 2. References require &s and `mut &`s instead of C++ implicit references. 3. Int -> FP conversions require a typecast In every case, both Rust and C++ allow you to discover the runtime behavior by reading the source code. But I would argue that Rust is more explicit than C++ in every case, wouldn't you agree? A feature of Rust that is not implicit, but also not local, is method resolution Isn't method resolution intimately tied to Deref coercion, which allows a type to implicitly (Rust's language) implement methods of another type? So method resolution seems like one of the more implicit features within Rust. but all of it is explicit if you look at the impl blocks for Vec<T>. Well, all of Ruby's monkey-patching is explicit in the sense that you can find it if you know where to look. It's a good effort to refine the meaning but "local" IMO is the best one!
- coderkd10 9y ago> Source code conveys everything possible about your program in any language. I disagree with this statement. Behaviour of the program will be determined by machine instructions that the compiler generates for a given source plus the machine environment where these instructions will be run. And it is not guaranteed that the generated instructions will be same for a given source across different architectures and environments that the compiler is run (plus I guess there is generally some degree of non-determinism in the compilers as well, because of the different optimizations it can make under different conditions, which are not "explicit" from the source itself). As far I understood, in the notion of explicitness that is defined in the article, it is defined that the language where source almost completely specifies the behaviour of program, irrespective of the compiler environments where it is compiled on, is an explicit language. I think in the sibling comment https://news.ycombinator.com/item?id=16034541 https://news.ycombinator.com/item?id=16034541 bad_user articulates more clearly the point I was trying to make.
- awfullyjohn 9y agoNot sure what he was going for with that definition of "explicit." It wasn't explicit at all. > you can figure out a lot about your program from the source of it. How does "implicit" not satisfy this condition? I can tell a lot about a program from the source of it implicitly as well.
- deleted 9y ago[deleted]
- deleted 9y ago[deleted]
- gravypod 9y agoWhat bothers me about languages like Rust, which I think I'm in the minority on, is the lack of explicit type declarations. C and Java, my two first languages, strictly spell out what types they expect. Sure you can ignore those rules but as long as you don't those types convey a lot of useful information about your program. With languages like Rust I don't think I could ever start writing code in them without an IDE. The entire idea of compiler-specified types is neat but I don't think all of your code should rely on that. One oddity is Python which I have used a lot. The only difference is that Python is much less strict than the languages I'm used to. Because of this learning Python was still relatively difficult (Why is all the documentation written like a book!? I miss my Doxygen) but I didn't need an IDE.
- twic 9y agoIn Rust, you still have to declare types for function parameters and return values. So, if you prefer to declare types everywhere, break your code down into single-expression functions!
- chewbacha 9y agoAnd even then, you are still allowed to explicitly define types everywhere, they are just optional. https://play.rust-lang.org/?gist=24d87fde3cc5273d4ec73ba5647d733a&version=stable https://play.rust-lang.org/?gist=24d87fde3cc5273d4ec73ba5647...
- oblio 9y agoI have bad news for you, local type inference is coming to Java :)
- hyperpape 9y agoInterestingly, even Java is probably going to introduce local variable type inference using syntax somewhat like let foo = bar(); http://openjdk.java.net/jeps/286 http://openjdk.java.net/jeps/286
- sidlls 9y agoI'm torn on this. I prefer explicit types in declarations as well, but very much like the convenience of inferred types. I find myself thinking, though, that the demand for the convenience of inferred types in these languages is a result of the verbosity in the type specifications themselves, usually with generics (Rust) or templates (C++). I rarely use the convenience of inferred types for concise type labels (e.g. non-generic structs, integers, etc.). Maybe this is a deficiency in the languages' designs?