News for hackers. Stuff that matters.
Re:Storm 2.0 by vbezhenar on Sunday June 02, 2019 @11:01AM (#20075875)
Java is abstraction over JVM which is abstraction over machine code. But I don't need to know anything about JVM bytecode or machine code to write typical Java code. Good abstraction does not require decompression. You're not going down to assembly to understand some Java code. You think on Java code level. That is good abstraction. If you need to decompress what you're reading, then it's a leaky abstraction. It's okay to use leaky abstractions to reduce repetitions, for example. But ideally your abstractions should not require one to learn its implementations in typical cases. For example if your function name is good enough, reader could trust you to do the proper thing and not read its implementation.
Re:Storm 2.0 by fauigerzigerk on Sunday June 02, 2019 @03:18PM (#20077401)
>Good abstraction does not require decompression

I think there's a misunderstanding. What I'm calling decompression has nothing to do with digging into the implementation of a particular abstraction. What I mean is merely tracking down all the indirections in the public interface and breaking them down to their concrete meaning in a specific case.

Some languages allow for a lot more moving parts than others. For instance, in Java obj.otherName means that otherName is an instance variable (or theoretically a class variable) and access time is guaranteed to be constant (tbd: caveats). It's not redefinable as it is in C#, Python or Swift. So there's one less thing to track down but also less flexibility.

Or take an extreme example like Go's range loop. It's defined only for a handful of builtin data structures. When you see a range loop, you know what it does without following any further indirections. It can be extremely annoying and create a lot of friction when you have to work with custom data structures. But it can make other people's code easier to read than in other languages.

Or take something like this:

  a == b
This simple expression has a far greater number of possible meanings in a language that supports operator overloading and generics than in a language that doesn't.

So transforming an expression's possible meanings into its concrete meaning is what I call decompression. There may not be a need for looking anything other than public interfaces.

Also, you're talking about abstractions purely from the perspective of users. But we are often creators and maintainers of abstractions as well when we model a particular problem.

Re:Storm 2.0 by Jach on Sunday June 02, 2019 @07:04PM (#20078983)
I think the better word you're looking for might be "reify" rather than "decompress". But there is something here that I can relate to. A long time ago I also made a comparison between various languages of "what do you have to understand to fully understand a Hello World program?" An interesting followup to that would be how much you have to understand on top of that to understand a more useful program.

You might be interested in this book, Patterns of Software, which brings up the issue that inheritance in OOP isn't about reuse but about compression and how the implications of that are why it's not had that much success in following through on the "reuse" promise. http://dreamsongs.com/Files/PatternsOfSoftware.pdf

Re:Storm 2.0 by TeMPOraL on Sunday June 02, 2019 @01:53PM (#20076930)
Abstractions are a spectrum. There's always a degree of benefit to be had from peeking under the hood. I'd argue that it's rare that you find an abstraction that can be used well without having to understand, or "decompress", some of it.

Consider JVM and Java: that you can write Java seemingly without any knowledge about JVM is an illusion - you already learned a lot about how things like JVM work under the hood when first learning programming[0]. Learning more about JVM itself lets you write more efficient code and debug better.

Consider functions: it's near-impossible to contain all the information necessary to use a non-trivial function in its header[1]. That's why good code contains comments and other forms of documentation describing the abstraction in more details. Even then, it's not always enough - sometimes it's really much easier to understand what you need by reading the source[2].

Consider any appliance - be it a car, or a radio, or a dishwasher. You can use it to it interface, to some extent at least. But knowing what's going on under the literal hood really does help with use, and especially helps when something goes wrong. If you don't know what's hidden under the abstraction layer, any failure will likely be incomprehensible to you and leave you helpless.

--

[0] - In theory, it might be possible to learn some programming without learning anything about hardware or hardware-emulating abstractions. In reality, I've never seen it or heard of it, and I suspect that the simplest mental model of code execution is isomorphic to somewhat simplified computer or virtual machine.

[1] - Function name + name of its arguments + types of its arguments and return value, if available.

[2] - Then again, implementation code may not capture the entire abstraction either. That's why good code often features comments inside the implementation, explaining the rationale behind some of the less obvious code parts.

Re:Storm 2.0 by abc_lisper on Sunday June 02, 2019 @01:44PM (#20076876)
You just explained cornerstone of good design