if (systemcall(“some string”, expression_argument(args), SC_MODE_1 | SC_MODE_DEFAULT) != 0)
if (0 != systemcall(“some string”, expression_argument(args), SC_MODE_1 | SC_MODE_DEFAULT))
One may find it easier to read/navigate flow control in C code that returns status codes, when these codes are stated beforehand. When there are series of long lines and a mix of 0==success and 0==false, it is easy to get lost, at least in my experience.
> Leave a comment there explaining the assignment.
Please don't. This is a perfectly understandable idiom in C. Don't explain the language in your comments; that's the job of a text book, which should be read by anyone before they read your code.
Which is great if your project treats warnings as errors. Not sure how common this is though since every time I compile a C program it’s just pages and pages of warnings.
Exactly. All code I write must pass -Wall -Werror -Wextra and there's always a debugging phase once you have written the code since there are syntax errors and whatnot, a lot.
A useful aspect of yoda notation is that it often makes an equality test easier to read because the constant is shorter than the expression it is tested against, and the == sign comes right away, not buried far away in the line.
Not all languages allows chained assignment (a=b=c) like c++ does, which is why we have this problem (and probably does not automatically cast them to bool either)
I know I'm in the minority, but I honestly never really understood why people get so up in arms about this. People keep saying it's so difficult to read, and I just don't understand why. I know that linters and such can catch this most of the time, but a lot of places I've seen don't use them. (I don't know why, that's a whole other discussion.) It just seems to me that it's something that keeps you from wasting time on silly mistakes should be common place. I really don't understand.
You must be young, friend. The holy wars that used to rage over just where to put curly brackets...
(And then Python came along and was like, "U wot mate?", and there were had little wars over "syntactically-significant indentation" and tabs vs. spaces, and how many spaces... And on, and on...)
Oh no, I'm not young. I just find this particular argument makes less sense than all the other types of arguments like this. Bracket placement in some languages is necessary to not have unintended effect. Tabs vs spaces can cause problems with certain ides/editors. I can somewhat understand most justifications as to why people have a certain reason for formatting code in their particular way. You want me to indent 3 spaces instead of 2 in Delphi, because that's the way you've done it, fine. I don't care. But this particular one, I don't get it. I never have. The amount of time that this one particular trick saved me in terms of time and frustration is huge. When you spend 45 minutes tracking down a problem because you assigned 5 (or something) to variable by accident, it almost always leads to a mouse throwing event. When someone comes back and says that seeing 42 == x is too difficult to read even though it can save countless hours, I just don't understand. (not every project has the benefit of having a linter or a compiler that will catch things like this.)
Code is for humans. If your language lets you make silly mistakes maybe it needs to stop doing that. Why can I assign during a branch? It's unnecessary.
Are they really easier to read though? A lot of the time which variable being tested is obvious, so it makes sense to put the important information - the value - first.
Despite the name, it isn't referring to Yoda's grammar form, it's just reversing things around "and" and "or". If you really have a problem telling that "x == y" is the same as "y == x" I suggest coming to a deeper, more complete understanding of the equality operator as a commutative operator where the order doesn't matter rather than thinking of it as "variable is? value", as so many students clearly pick up accidentally.
I've actually noticed one thing about Common Core is that they do try much harder than when I was a kid to not accidentally create that impression; my kid's homework is full of "4 + 3 = ___" followed immediately by "____ = 8 + 2". Still kind of glossing over "=" as a "simplify" operator, but it's still an improvement over when I was a kid when it was really easy to pick up the idea that the "=" operator was actually a function meaning "take the expression on the left and simplify it". (I mean, there's a sense where such students aren't even wrong; it is the rational conclusion from the evidence presented.)
> If you really have a problem telling that "x == y" is the same as "y == x" I suggest coming to a deeper, more complete understanding of the equality operator as a commutative operator
Code is for humans, not computers. The order I choose when writing an expression is driven by what I want to convey to the next person reading my code.
`if (button.state == .enabled)` suggests to the reader that the button’s state is the thing we’re interested in in this particular piece of code. Reversing the operands is confusing not because I don’t understand the communicative property, it’s confusing because it puts the emphasis on the wrong thing: I’m not checking if the enabled state matches an expectation, I’m checking if the button’s state matches an expectation. And I want the reader to understand that.
The first sentence uses active voice - the second passive. Active voice ascribes agency to X; It makes a subject/object distinction between X and Y. Passive voice makes them both objects.
When reading code, it makes more sense to ascribe agency to variables than to constants, which is why people are more comfortable reading x == 0 than 0 == x. Zero can’t change, so it can’t do anything to make itself equal something. X can change, so it is capable of equaling things.
If you’re equally comfortable with either formulation, maybe you just prefer the passive reading of the sentence.
But I do wonder if you’d be equally happy if I went through your codebase and replaced every for loop condition from i < length to length > i...
> Still kind of glossing over "=" as a "simplify" operator, but it's still an improvement over when I was a kid when it was really easy to pick up the idea that the "=" operator was actually a function meaning "take the expression on the left and simplify it".
What? No. De '=' sign is very simple: what's written to the left of it is equal to what's written on its right.
So I'm writing a unit test. I bet everyone here can correctly guess the language.
assert ('Content-Type', 'text/plain') in dupefail.headers
assert b"registration denied" in dupefail.body
assert "403 Forbidden" == dupefail.status
I also happen to pay attention to the linter fart^Woutput:
C: 61,11: Comparison should be dupefail.status == '403 Forbidden' (misplaced-comparison-constant)
I totally admit my thorough hate of pylint, it hasn't really ever helped me once -- mostly led to more `#pylint: disable=…` garbage in the source. I still force myself to use it, as a duty by fellow... other engineers. But that's an aside.
Please, tell me how much more "natural" and "un-ugly" the 3-line snippet would read to you had it the third line assert flipped away from Yoda style, just as pylint suggests. I'm eager to hear you.
Look, I'm trying to humanly argue against the statement "Yoda conditions are unnatural". Nature has no boolean conditions. That statement should instead say "Yoda conditions are unfamiliar (to me)" -- at which point it's way easier to see the statement's applicability limits, and dramatically narrow down its consequences.
On the contrary; there're many common contexts where Yoda comparisons looks more "natural", meaning they avoid breaking the surrounding code flow, and bring the important part (the constant) up-front. I even brought up a real-world example. Having read `assert "403 Forbidden" == ` and remembering the context, can't you already guess the RHS (and just skim over it)? Sure you can. Non-yoda loses here.
Be aware: you don't have to take a "for/against" side in this debate, as our buggy brains try to in every flame war. Both sides have a point. Familiarize yourself, and decide on case-by-case basis.
While we're at it: self.assertEqual() is super-ugly and unnatural, in my judgement. Why am I forced to use _thrice_ as much words to express the simple single-word concept of an assert? Why can't I spare the extra pair of parens, and spell == directly? I see nothing wrong with bytecode rewriting; it's amazing they can do it, and I appreciate the effort.
Treating the cause's cause: use a programming language which makes a distinction between actions and values, so that an action-which-produces-a-boolean is not valid where a boolean is expected.
Treating the cause's cause's cause: design your own programming language to be a strongly typed functional or logic programming language that is a descendant of the ideas in XSLT, where the attitude was “the most common thing you do in programming is to map one data structure into another, so let’s build the whole language around making those mappings easy first.” There can now be no confusion.
Probably treating the cause's cause's cause's cause is something like “just use Excel for everything, why are you using these other languages?”
Alternatively there are languages, where this problem can't arise at all.
In Clojure for example: (= ...) just tests for (actual) equality, while (def ...) assigns a symbol to a value, or (swap! atom f) changes the value of an atom (reference type).
I once worked for a place that explicitly told me not to do this. They also told me to test booleans with
if( booleanVariable == true ) ...
This was also the place that ordered me not to use LINQ statements because, and I quote, "you need to write code that someone fresh out of high school could understand". I don't work there any more.
We actually have to write boolean checks like that in Kotlin nowadays in modern Android development. If your variable type is Boolean? instead of Boolean, it is needed to both check if it is non-null and true.
There are zero reasons to use that ugly and unnatural Yoda notation in 2019.
Deleted Comment
Likewise:
Or something like that. I don't understand the hate, just make sure it's obvious what you're doing.Please don't. This is a perfectly understandable idiom in C. Don't explain the language in your comments; that's the job of a text book, which should be read by anyone before they read your code.
But enabling it on the language level brings a large amount of risk and complexity just for what amounts to a micro-optimization.
It also reduces time in debugging as you catch it immediately.
It's my favourite way of writing if statements.
Deleted Comment
Deleted Comment
(And then Python came along and was like, "U wot mate?", and there were had little wars over "syntactically-significant indentation" and tabs vs. spaces, and how many spaces... And on, and on...)
Both sides of the equality check are equally important.
I've actually noticed one thing about Common Core is that they do try much harder than when I was a kid to not accidentally create that impression; my kid's homework is full of "4 + 3 = ___" followed immediately by "____ = 8 + 2". Still kind of glossing over "=" as a "simplify" operator, but it's still an improvement over when I was a kid when it was really easy to pick up the idea that the "=" operator was actually a function meaning "take the expression on the left and simplify it". (I mean, there's a sense where such students aren't even wrong; it is the rational conclusion from the evidence presented.)
Code is for humans, not computers. The order I choose when writing an expression is driven by what I want to convey to the next person reading my code.
`if (button.state == .enabled)` suggests to the reader that the button’s state is the thing we’re interested in in this particular piece of code. Reversing the operands is confusing not because I don’t understand the communicative property, it’s confusing because it puts the emphasis on the wrong thing: I’m not checking if the enabled state matches an expectation, I’m checking if the button’s state matches an expectation. And I want the reader to understand that.
> X equals Y
> X and Y are equal
The first sentence uses active voice - the second passive. Active voice ascribes agency to X; It makes a subject/object distinction between X and Y. Passive voice makes them both objects.
When reading code, it makes more sense to ascribe agency to variables than to constants, which is why people are more comfortable reading x == 0 than 0 == x. Zero can’t change, so it can’t do anything to make itself equal something. X can change, so it is capable of equaling things.
If you’re equally comfortable with either formulation, maybe you just prefer the passive reading of the sentence.
But I do wonder if you’d be equally happy if I went through your codebase and replaced every for loop condition from i < length to length > i...
What? No. De '=' sign is very simple: what's written to the left of it is equal to what's written on its right.
Deleted Comment
Deleted Comment
Please, tell me how much more "natural" and "un-ugly" the 3-line snippet would read to you had it the third line assert flipped away from Yoda style, just as pylint suggests. I'm eager to hear you.
To properly support assert with good error reporting, pytest has to rewrite the byte code. See http://doc.pytest.org/en/latest/assert.html#assert-details
On the contrary; there're many common contexts where Yoda comparisons looks more "natural", meaning they avoid breaking the surrounding code flow, and bring the important part (the constant) up-front. I even brought up a real-world example. Having read `assert "403 Forbidden" == ` and remembering the context, can't you already guess the RHS (and just skim over it)? Sure you can. Non-yoda loses here.
Be aware: you don't have to take a "for/against" side in this debate, as our buggy brains try to in every flame war. Both sides have a point. Familiarize yourself, and decide on case-by-case basis.
While we're at it: self.assertEqual() is super-ugly and unnatural, in my judgement. Why am I forced to use _thrice_ as much words to express the simple single-word concept of an assert? Why can't I spare the extra pair of parens, and spell == directly? I see nothing wrong with bytecode rewriting; it's amazing they can do it, and I appreciate the effort.
https://rencore.com/blog/powershell-null-comparison/
Treating the cause: Use static analysis.
Treating the cause's cause's cause: design your own programming language to be a strongly typed functional or logic programming language that is a descendant of the ideas in XSLT, where the attitude was “the most common thing you do in programming is to map one data structure into another, so let’s build the whole language around making those mappings easy first.” There can now be no confusion.
Probably treating the cause's cause's cause's cause is something like “just use Excel for everything, why are you using these other languages?”
It's be harder to get things done, but we'd be more certain about them
In Clojure for example: (= ...) just tests for (actual) equality, while (def ...) assigns a symbol to a value, or (swap! atom f) changes the value of an atom (reference type).