Hacker News new | ask | show | jobs
by Tainnor 1073 days ago
I'm not sure why you think that quoting random HN users proves anything except personal opinions of specific people? These are fine, but other people have other opinions.

I don't oppose the "principles" you've quoted, but they would just as easily apply to e.g. Haskell (maybe except for the "there's only one way to do it" which however has never been true of any language, including Python).

I feel like you missed my larger point. It's not terribly difficult to write code that you can understand line by line. It's incredibly hard to write a huge code base in a way that you can reason about many code paths simultaneously, however. That's where the abstractions start to make sense.

I don't understand why people think that those facilities were created just to piss people off? People were facing real problems. Yes, sometimes the cure is worse than the disease. Use abstractions judiciously and by employing common sense. That doesn't mean you should never use them.

I've seen over- and underabstracted code (as well as just plain wrongly abstracted code). Both of these situations really suck.

Honestly, what annoys me a bit here is your smugness. It seems as if you feel you've figured out how to write good code, and all the other idiots who use Ruby, Java, etc. haven't. But I don't believe you. Nobody in this industry knows how to write "good" code. I don't even think we know what "good" code is. The most we can do is try our best, learn about better ways to do things, discuss approaches and use our judgment.

2 comments

> I'm not sure why you think that quoting random HN users proves anything

Does it have to?

How do you prove that what someone expresses is something other than opinion when it comes to programming practices? This isn't a field that is easy to quantify or distill into unquestionable truth. To approach anything nearing proof we'd need data from which clear conclusions can be drawn. A look at scientific publishing on a lot of these topics suggests that "proof" is going to be hard to come by for a lot of the things discussed here.

> but other people have other opinions.

Not all opinions count equally to all people. In fact, most people's opinions don't matter. However we do tend to value the opinions of people who are able to properly articulate reasonable arguments based on demonstrable results or experience.

I'm not looking for rigorous proof, but these are just cherry-picked example quotes instead of a coherent argument. You could just as well quote people who have experience dealing with code that is "not clever enough", e.g. 1000 line files without any internal structure. What does that show?

Writing code is about tradeoffs and not about pithy truisms lime "code should be obvious".

I'm afraid "writing code is about tradeoffs" is just as much of a truism. It's not going to help anybody write beter code. You need to get into the specifics.
The difference is that I didn't presume I could give anyone easy advice about how to write good code.

The only thing you can do is gain lots of experience, constantly question if there are better ways to do things, read about ideas others have had (without getting religiously attached), make your own mistakes, hopefully learn from them, overcorrect, then learn from your overcorrections and so on. I'm afraid there's not really an easier way.

On the other hand "write obvious code" makes it sound as if there's an easy way to do it, and everyone who doesn't write "obvious code" is just deluded, showing off, or something like that.

> On the other hand "write obvious code" makes it sound as if there's > an easy way to do it, and everyone who doesn't write "obvious code" > is just deluded, showing off, or something like that.

There is nothing easy about writing code that is obvious to other people. After all, the point of the exercise is how you communicate ideas clearly to people with the goal of amplifying their productivity. That takes time, empathy, and a willingness to study how other people understand things and accepting when you are not getting through to them.

Most programmers are not good at this. Worse yet, most programmers won't try to be good at this and instead go looking for simple truths. At best, most programmers obsess over "best practices" without really asking themselves if these are the best way to communicate a given idea or if there is a clearer way. To dare to do what's better, yet respect when "better" isn't necessarily better for other people.

(Erik Spiekermann, a designer of typefaces, made an observation that is useful with regard to the last statement. Erik has no love for the font Arial. He doesn't think it is a very readable font. However, he also points out that it is a font most people are so familiar with that even though he thinks its design is poor, it is actually a good functional choice because so many people are used to it that their familiarity makes it easy to read text typeset in Arial).

If your attitude is that it isn't worth trying because it isn't easy to do, then I'm sorry for you, but I think your value to an employer will be limited to only the output you can produce yourself. The biggest potential for a programmer is in their ability to amplify other programmers. And that starts with being able to communicate clearly. Both at the micro level, in code, and at the macro level, in terms of clear structure, abstraction and architecture.

The best way to ensure you don't evolve into a programmer who is able to amplify other programmers, and provide value beyond your own immediate output, is to not even try.

> If your attitude is that it isn't worth trying because it isn't easy to do

I haven't said that and I don't appreciate you insinuating that I don't care about writing good code.

So if it isn't about trying to make things obvious, what do you think the goal is?
Huge code bases are never gonna be "obvious". It's all about optimising for a balance of tradeoffs.
So you claim that beyond some magic size limit a codebase cannot be easy to understand. Well, quantify it. At what number of lines of code does a codebase pass from the domain where it is possible to easily understand it to where it is impossible?

I suspect you didn't pay any attention to what I wrote about how people go about ensuring that large codebases maintain readability. That saddens me a bit because it means you probably aren't interested in learning anything.

This is just an incredibly bad faith reply, and an insulting one at that. I don't know why you felt the need to cross into personal territory, but I will make a mental note not to engage with you again.

PS, please check my comment history before claiming that "I'm not interested in learning anything".

> I'm not sure why you think that quoting random HN users proves anything except personal opinions of specific people? These are fine, but other people have other opinions.

They support my argument so I included them. I don't see a practical difference between a "random HN user" and a random blog post or anything else. A good idea is a good idea, regardless of the medium.

---

> I don't oppose the "principles" you've quoted, but they would just as easily apply to e.g. Haskell

Possibly, I threw it together pretty quickly, so it's not very thought-out. I'm also not familiar enough with Haskell to know what you mean.

---

> (maybe except for the "there's only one way to do it" which however has never been true of any language, including Python).

It's not binary, but a spectrum. No language has just literally one way to express each concept. However, Python is definitely further towards the "one way to do it" end of the scale. Perhaps not as much these days as it used to, but still far more than for example Ruby or Perl.

---

> I feel like you missed my larger point. It's not terribly difficult to write code that you can understand line by line. It's incredibly hard to write a huge code base in a way that you can reason about many code paths simultaneously, however. That's where the abstractions start to make sense.

I thought I adressed that; everything I mentioned - explicit error returns, pure functions, no global state, and no metaprogramming - all show their true worth in large and/or unfamiliar codebases.

---

> I don't understand why people think that those facilities were created just to piss people off? People were facing real problems. Yes, sometimes the cure is worse than the disease. Use abstractions judiciously and by employing common sense. That doesn't mean you should never use them.

I'm not sure what exactly you mean by abstractions, so this is hard to respond to.

---

> I've seen over- and underabstracted code (as well as just plain wrongly abstracted code). Both of these situations really suck.

Both suck, but as far as I can tell, erring on the side of underabstracting is better. Some random references (not HN comments ;>): [1] [2].

> Honestly, what annoys me a bit here is your smugness.

;) I can either post something quick but smug or spend hours polishing it until it's as bland as can be. I prefer the quick and authentic approach.

---

> It seems as if you feel you've figured out how to write good code,

Not even close.

---

> and all the other idiots who use Ruby, Java, etc. haven't.

I'm definitely not calling people who program in <x> language idiots. There are far too many factors at play to be able to make such a broad judgement.

---

> Nobody in this industry knows how to write "good" code. I don't even think we know what "good" code is.

I'd certainly hope that in the last half a century of programming we have at least learned something! A video (and book) you may enjoy: [3].

---

> The most we can do is try our best, learn about better ways to do things, discuss approaches and use our judgment.

I thought that's what we were doing.

---

[1] https://sandimetz.com/blog/2016/1/20/the-wrong-abstraction

[2] https://programmingisterrible.com/post/176657481103/repeat-y...

[3] https://www.youtube.com/watch?v=bmSAYlu0NcY

> I thought I adressed that; everything I mentioned - explicit error returns, pure functions, no global state, and no metaprogramming - all show their true worth in large and/or unfamiliar codebases.

I agree with all of those. I try to avoid these things whenever I write code (in rare cases, there are valid reasons for using them, but I agree they are overused).

But that still leaves tons of room for different ways of writing code, and it's very hard to say which one of these is "obvious". Obvious to whom? Some people want to have large methods, so they can see everything at a glance, others prefer to have more smaller function so they can see the high-level picture before they see the details. Which one of them is right? I can't say - it depends on the person, on the problem, and on many other factors.

What is missing from your list is "don't use advanced language features". You can do all the things you mentioned and still use "advanced" language features. And the debate about Go is often about how (presumably) the absence of "complex" features (something which is IMHO a bit subjective) makes code more "obvious".

But you can have generics (or, more broadly, polymorphism), interfaces, higher order functions, proper algebraic data types, etc. and still uphold all the features you've quoted. That's what I meant with the Haskell comment (but supposedly the same would be true for e.g. Lisp).

Since you shared a talk with me (which I intend to watch, but I haven't had time yet), allow me to also share one (with which you may already be familiar): https://www.infoq.com/presentations/Simple-Made-Easy/

Here, Rich Hickey (the creator of Clojure) makes a point that resonates very well with me: namely that simplicity (which is what we desire) is not the same thing as easiness, and that pursuing the latter can often come at the expense of the former. In other words, if you use "advanced" features the right way, it can help create code that may require more concepts, but is still simpler to reason about.

> https://sandimetz.com/blog/2016/1/20/the-wrong-abstraction

I've never taken this blog post to mean that abstractions are wrong. She does say that a bad abstraction is worse than no abstraction - but, IMHO, also that the right abstraction is even better than that. BTW, Sandi Metz is a Rubyist.

> Both suck, but as far as I can tell, erring on the side of underabstracting is better.

Maybe you haven't had the fortune of working with code written by non-developers (e.g. data scientists). But in any case, my most common experience is that most abstractions are simply wrong. Code that belongs together is spread out over 5 files, and these in turn don't have a single purpose, but end up doing too many things at once. Of course, I've also seen overabstracted "every class has an interface" nonsense. And I've seen huge functions that would have benefited from some internal structuring.

> ;) I can either post something quick but smug or spend hours polishing it until it's as bland as can be. I prefer the quick and authentic approach.

Well, this comment that I'm replying to doesn't seem bland to me. You elaborating your point of view makes for more interesting discussion - at least in my view.