Live data from Hacker News

Read this post ‘unless’ you’re not a Ruby developer

jesseduffield.com

101–110 of 326 posts

Re: Read this post ‘unless’ you’re not a Ruby developer

#102
IMHO, 'unless' in Ruby works best for single checks. It's just a convenient form of 'if not'. That's about it.

I always insist on not using 'unless' if it's not clearly readable as an english phrase or if there's an 'else' as well.

A similar pattern I follow with 'if !'. If there's an 'else' condition always put the positive check first and the negative one in the else, rather than the other way around.

Footguns are equally possible using complex 'if !' statements.

Re: Read this post ‘unless’ you’re not a Ruby developer

#103
post #5

The worst thing about `unless` and double negatives, is having been raised in a culture with different double negative rules than English. In Italian a double negative is still negative. I know boolean logic pretty well, but `unless !something` still trips me up to this day.

> In Italian a double negative is still negative. Same in Spanish! I think you're making a very good point here – understanding "unless" (quickly, i.e. without having to think about it) very much depends on one's understanding of the English language and/or one's mother tongue. Sure, one can probably get used to it (like one gets used to what "if/else" means etc.), but it definitely increases the mental effort needed…

In Spanish I usually translated double negation like this:

"No! (Wrong!) There is no ..."

Bringing it back down to 1 level of negation, for it to make logic sense again.

Re: Read this post ‘unless’ you’re not a Ruby developer

#105
post #98

I really don’t understand the author’s point about adding extra conditions. They admit that many people will find a single condition with `unless` more readable. They then complain that it becomes unreadable when adding another condition. OK, so swap it out for an `if` at that point. No one is forcing you to keep using `unless` if the requirements change. “You should use a suboptimal solution to cater for unknown fut…

I believe this is somewhat prevalent in the Ruby community as of late where people try as hard as possible to "lock down" the language and limit the ways you can get to a solution in the name of the proverbial "ease of understanding". I wholeheartedly disagree and believe we should instead grow the developers to understand these different approaches as opposed to labeling half of the language "bad practice". As I sai…

I love an expressive programming language, it’s why Go makes me feel like I’m brushing my teeth with sandpaper…

But there’s such a thing as too much flexibility, expressiveness and flexibility often go hand in hand as flexible language lets you make things as expressive as you want… but things can be expressive without the same level of flexibility if they are well designed.

I find Rust strikes a good balance for low level language work, it feels more expressive than C because of higher level language features but it’s not necessarily as flexible as C with things like the borrow checker nagging you to be safe unless you turn it off.

Lisp… too flexible, too expressive. Lisp code reminds me of the phrase “that depends on what the definition of is, is”.

Scheme and scheme likes including weird step cousins like JavaScript share the unfortunate result of this and your drowning in custom DSLs and no one quite codes the same way unless you have rigorous tooling to enforce a team style.

Ruby falls foul of this for me too. It’s too flexible, it’s very expressive and I enjoyed reading the tutorials and learning the basics. But the moment I discovered real code I was immediately recoiling in horror …. It was a disaster… a spaghetti mess of overrides redefining and meta-programming in general. It made it impossible for me to ever trust the environment I coded it since I had to constantly inspect everything to make sure someone hadn’t done something crazy like enhanced the “+” sign to transform numbers to strings for avoiding something like a sql injection risk in a specific context and whoopsie, leaked the behaviour globally so now any time you added integers you got concatenated strings… but only after the library was dynamically loaded on first query … maddening stuff…

Stuff like this is why ruby is too flexible.

Re: Read this post ‘unless’ you’re not a Ruby developer

#106
post #35

Earlier quoted context omitted.

It's not pointless, it makes code read better. It's another option to have. It's not meant for every use case. It indicates you don't understand Ruby if you find yourself using an "unless" in a complex boolean operation. It's meant for simple cases like an inline return statement return unless User.exists(id=100)

I'll admit I'm not a Ruby developer, but wow it allows return conditionally inside an expression? What were the language designers thinking?! I can't think of any other language that allows return inside an expression (or break/continue). Let's see: C, C++, C#, Python, Javascript, Object Pascal, Java, Rust; all nope. That is indefensible.

It's not doing "return conditionally inside an expression". The above statement is equivalent to:

   if !condition
     return
   end
In other words, the return in question has no argument. The unusual (but not unique) aspect of Ruby here is that if/unless can suffix the "then" block and not just prefix it.

Re: Read this post ‘unless’ you’re not a Ruby developer

#107
on a project about a decade ago I had written some ruby code in a non-rubyish manner (non-rubic?) in that I had written if statements.

I had actually decided to write them as if statements because that way I didn't have to make one particular logical check (I can't really remember what the logic was, just that it had to do with language and Swedish language legal documents did not have a particular rule that Danish ones did.

So a senior Ruby dev who admittedly was a lot better than me in a lot of things but did have the habit of making incredibly boneheaded bugs sometimes, went through and rewrote all my if statements as unless statements - inadvertently reversing the logic.

A week later bug comes up I get blamed because it was the thing I worked on I was embarrassed, and I went through the code fixing but then I thought - wait I wouldn't have written this as an unless because I need to do one extra statement that way! After digging through I caught our senior dev, the very guy blaming me for causing bugs.

Ah the revenges of youth are very sweet.

Re: Read this post ‘unless’ you’re not a Ruby developer

#108
post #61

Earlier quoted context omitted.

I'll admit I'm not a Ruby developer, but wow it allows return conditionally inside an expression? What were the language designers thinking?! I can't think of any other language that allows return inside an expression (or break/continue). Let's see: C, C++, C#, Python, Javascript, Object Pascal, Java, Rust; all nope. That is indefensible.

If and unless can be used as post-fix clauses. Also, in ruby, -everything- is an expression, so... of course you can return from there

This isn't exactly true. It's a syntax error to put a return anywhere where the grammar expects a value expression, because it's one of few constructs in Ruby that doesn't return a value (contrast with e.g. "if" and "def" and "class", all of which return a value).

E.g. "42 == (return true)" is a syntax error while "42 == if false; true; end" is syntactically valid.

You can return in the expression in the comment above because the return is at statement level - nothing above it in the grammar requires a value (but obviously allows it).

Off the top of my head I can't remember which other keywords fall in that category. Obviously "end", "then", "alias" and there'll be a few more, but for most keywords in Ruby you're right they can be treated as expressions.

Re: Read this post ‘unless’ you’re not a Ruby developer

#109
post #68
post #15

Earlier quoted context omitted.

To be fair, Ruby inherited "unless" from Perl. And Perl literally has the opposite design principle, TIMTOWTDI or "there is more than one way to do it". I'm not arguing here -- I prefer the "one obvious way" principle. But you can design a beautiful programming language without regard for the long-term learnings of software engineering. I always liked Perl's "unless", and I always made sure to not abuse it with doubl…

I only know `unless` from Perl, and it can make your code clearer if used sparingly. For example it allows you to express preconditions positively: die "You may only use port numbers 1024 and higher" unless $port >= 1024;

    die "Port numbers below 1024 are forbidden"
        if $port 
is hardly unreadable spaghetti code.

Re: Read this post ‘unless’ you’re not a Ruby developer

#110
post #79

Earlier quoted context omitted.

God that's such a landmine when reading code. Seeing a return without an explicit change of scope... Why ? To save one line ? Yep that's why I hate ruby - worked on one mature codebase for a year and after seeing various such gems used across the project - from >10 devs - I'm confident I will never touch the language again.

Those one line returns are particularly handy at the beginning of methods, to validate or process arguments and return immediately for simple cases.

Short circuiting is such a beautiful way of avoiding giant nested "if" mountains. I wish it was more widely used.
Post reply on HN