- Feature Articles
- CodeSOD
- Error'd
- Forums
-
Other Articles
- Random Article
- Other Series
- Alex's Soapbox
- Announcements
- Best of…
- Best of Email
- Best of the Sidebar
- Bring Your Own Code
- Coded Smorgasbord
- Mandatory Fun Day
- Off Topic
- Representative Line
- News Roundup
- Editor's Soapbox
- Software on the Rocks
- Souvenir Potpourri
- Sponsor Post
- Tales from the Interview
- The Daily WTF: Live
- Virtudyne
Admin
private static final COMMENT = "frist"
Admin
2 + 2 = FIVE; see this can be true, depending on what FIVE is. And on what true is.
Admin
Before I learned about C# named arguments, I used to do that, too. Yes, even with bools. Looking up method signatures might be a key press away or even a popup in most modern IDEs, but the same applies to a compile-time constant. Doesn't Java also have named arguments?
Overconvenience wrappers may be diminishing returns, but not harmful (unless for the explicit purpose of inflating one's SLoC, of course). Useful if one of them is being called far more than the other.
And SIX and FIVE is the rather plebian WTF of naming constants incorrectly, i.e, what they are instead of what they mean.
:mlp_shrug:
Addendum 2020-08-13 08:07: So, private static final int MIN_FOLDERS_IN_PATH = 6; And index of the last folder should probably be a local variable instead: int lastFolder = folders.length - 1.
Admin
Java does not have named arguments
Admin
In the old days (circa 1960s) the OS for IBM 360 mainframe computers had a bug that could cause "anomalous" results. In Assembler programming you could pass an integer parameter by reference to a function that would change the value of the parameter. If you passed in a hard coded value (e.g. 7) and the function changed the value to, say, 14, then all subsequent references in the program to 7 would be treated as 14. Could cause some interesting effects when indexing. And No, this was not a "feature" - it was a bug.
Admin
Extracting constants for 5 and 6 but not the file separator is genius. That's clearly been done for static analysis related reasons. There really should be a Checkstyle rule that checks that no constant is just a number with a name that is the word for the number - that's never useful. (Extracting that 5 and 6 as PATH_FOLDER_INDEX and MIN_PATH_DEPTH or something would be fair enough.)
Admin
I've reviewed some code that uses constants where the only use is effectively. If (value == 2) else if (value == 3) else if (value ==4) else continue.
To make matters worse one of the actions carried out under each if is exactly the same no matter what. Another action could be replaced by an action on value -1. The only other action only comes into play if(value==4) so if you checked for a valid value at the start of the routine you could collapse the entire construct down to far fewer lines. I wouldn't mind so much but I'm a data person spotting problems with Java code. Data people are apparently too thick to read Java.
Admin
Not even that old, nor that low-level a language. The FORTRAN compiler & runtime on VAX/VMS in the mid-to-late 1980's did exactly the same thing. My first job out of school, the boss showed me his code DOTHIS(&6); and I took his word that it was totally legitimate.
Admin
Eh, that separator is a separate (heh) WTF. It's totally the wrong way of finding path depth to begin with. I'm not invested enough to look, but there must be some function Java provides that takes care of all sorts of path mangling. But even if there isn't, if path value comes from some I/O function, it's File.separator. If it's from data or user input, could be at least either kind of slash.
Admin
java.nio.file.Path
has a function that counts the number of path components by the looks of things.Admin
when I was in school, they always said that when you use numbers in a sentence, you were supposed to spell out the first one. "There were four or 5 WTFs in that story." Maybe that explains it.
Admin
English majors writing software. Now there's the real WTF.
Admin
addDocument(act, FILE_NOT_FOUND) might actually make sense in this context.
Admin
Even PHP has the constant DIRECTORY_SEPARATOR.
Admin
The first part isn't so bad. Having descriptive method names even if redundant isn't always a bad thing. If used correctly there's no ambiguity as to wether the action sends a notification or not which is IMHO a good thing.
Now the constants for 5 and 6 though... yikes.
Admin
That's not English-major-level grammar. That's elementary-school-level English grammar. Time for someone to go back to school.
Admin
Admin
Create a nonverbose function. When called, notifications are off. Then a constructor, Document(act) like String(array)
Admin
It was a feature. The System/360 didn't have an "immediate" addressing mode (where the constant you want to load is embedded inside the instruction), so you had to load constants from somewhere. The assembler faked up a somewhere for you to load the constant from.
Addendum 2020-08-13 12:14: Er, but it folded all instances of a particular constant into the same "somewhere".
Admin
this is the kind of code that inevitably leads to...
private static final int FIVE = 3;
Admin
More likely just
DOTHIS(6)
without the & and the trailing semi-colon. Fortran requires neither(1). And that was a general feature of Fortran rather than a VAX/VMS-specific thing (and therefore the feature was older than the VAX), although Sun's Fortran compiler for Solaris/Ultrasparc that a former employer of mine used in the 2000s put this kind of constant in a read-only section, so a program that tried to abuse them in this way would crash and burn.(1) All function arguments are passed by reference in Fortran, even constants, which is why the trick could work.
Admin
Doesn't Fortran even allow passing a constant to a function that modifies the value? I'm not sure if crashing at runtime was a debug flag though...
Admin
The help provided by modern IDEs is not something you should expect as given and guaranteed everywhere and everytime, and you definitely should not understand it as a way to compensate and clean up WTFs. Sometimes souce code gets used in places that suffer from NIH when it comes to making the appropriate tools available to the developers, or where "just hire 10 more of those cheap coders, that'll work" is a valid excuse for "not going to spend all that precious money on those stupid licenses for that strange tool we never heared of". So in the end, you can see things like doActionWithDocument(ACTION100, "Bob", True, True, False, True, True, "", "", True, 100+4, -1, -2, "crm114.example.com", 80, "", "/", "", True, False, COLOR_GREEN). A good IDE will help you find out what the 3rd "True" was for. But if you're unlucky, you're the developer who is told that "Notepad is enough for you!" and "Comments just inflate the codebase, put them in that Excel table instead!". Even if you resort to a language that supports named parameters: There is potential to do it wrong. Think about something like this: IniTechUtils.performAction(sourceDocument = "Invoice030620-58672.doc", action = CREATE_PDF, format = ISO_A4, owner = 7652, group = "28", amount = 100.5, id = "", lastPaid = -1, target = IniTechInternalUtils.getTarget(), defaultResult = "Tony", checkForErrors = False, checkForErrors2 = False, additionalActionParameters = "3, 100, True, 299.95"). While it starts out promising, it ends in confusion. No programming language and no development tool can help you if they're not used properly, and especially not if no working human mind is involved.
Admin
That's totally false! Which means it IS true!
Admin
And on whether you've overloaded + and/or =
Admin
What's harmful is giving them less informative names, e.g. doActionWithNotification() instead of addDocumentWithNotification(). Mind you, knowing only what's given in the article, addDocument() is itself potentially confusing (add which document? add it to what? what are the different actions available? if there's a notification, then how does that work?), but some of these may be more evident after looking at the Document and Action objects (code and documentation).
Admin
Speaking of magic: http://catb.org/jargon/html/magic-story.html
Admin
The FIVE and SIX are awful name choices, but apart from that I can see why they're better than dropping in numeric values, it shows that there's a reason for having the value 5 there rather than just having it as an arbitrary magic number. In other words it's signalling to the person reading the code that this is a specific constant value, not a magic number pulled out of a hat.
Admin
In a general absolute sense, it cannot know since the function or subroutine might be in a different "compilation unit", but yes, it did allow you to do that. YMMV with later versions of Fortran, but Fortran 77 and earlier definitely allow it.
Fortran evolved in an era when programmers were expected to know what they were doing.
Admin
I do realize a lot of people (me included) don't quite have the luxury of telling their current or prospective employers to go fornicate their trilby hats regarding tools, but that would be a BOOL fRed (big red flag) in an interview with a company. And the whole shipment of flags if they lied (or lied by omission) about their tooling and you had to find about afterwards they don't provide any.
It's a common misconception that IDEs must help to write code. It then turns out many never did and still don't. Well yes, computers don't understand programmer's intentions, so they can't. A decent programmer must have the clarity of thought to write the general idea even on paper. But they usually do help to read, which I find at the very least just as important. For example, I can't imagine working without Find All References when reading even my own code.
As for named arguments: eh, everything can and will be abused. I tend to use them only to clear up ambiguous parts and to skip optionals.
Admin
@Steve_The_Cynic ref
S/360 certainly did have immediate ("SI") instructions with one immediate and one storage operand. Ref https://en.wikibooks.org/wiki/360_Assembly/360_Instructions
Now the immediate value was just a single byte. In a machine with a 32-bit word length & GP register width. The repertoire was pretty limited too:
store
,and
,or
,xor
, and a couple flavors of compare or bit-test.So, as you almost said, for many purposes constants ended up defined somewhere in ordinary writeable memory. And woe betide the programmer who passed one of those supposed-to-be-constant addresses into a routine that wrote a different value to it.
IME with assemblers of the day, any constant folding was done manually by the programmer. If you needed to add the fixed 32-bit value 42 to a register in 5 places in your code you could declare one word with initial value 42 and reference it five times or you could be sloppy and declare the same thing five times. The assembler would dutifully do what you asked in either case without protest or second guessing your work with a warning.
In maintenance it certainly was common to declare a redundant new constant for new code added to since you couldn't quite be sure that what appeared to be a similar constant was a) really a constant, and b) wasn't going to be changed by another maintenance action in the future for a reason that wouldn't apply to your use of 42. Given the pitiful code analysis tools of the day (i.e. large stacks of green bar paper, worn out printer ribbons, and human eyeballs) it was easier to be safe than sorry.
Admin
Those boolean constants should clearly be a two-value enum.
Admin
Named arguments are also useful for making sure you're not inadvertently passing multiple arguments in the wrong order.
Admin
Huh. You learn something new every day. Pity I didn't learn that 35 years ago, I guess.
OIn the other hand,
Programmers back then were, indeed, supposed to know what they were doing. As I said:
Admin
Replacing numbers with constants like FIVE or SIX is just replacing magic numbers with magic constants, less readability for no gain. And using constants for a boolean is almost as bad since sure, reading existing code gives you a little more context, but when writing you get no help since you need to know the constants to be used.
An enum or similar would have helped since it would either trigger intellisense or force you to locate the enum which will then give you readable code on every invocation of the method.
Admin
I had a very fun bug in some Fortran code in Windows in the early '00's due to accidentally changing the value of 0.0 via the same process (passed as an argument to a routine that modified the argument, in Fortran arguments are passed by reference). This was with the Digital Visual Fortran compiler, of mid-'90's vintage (not the latest, but still a reasonably modern-for-the-time Fortran 95 compiler). They changed newer compilers to put constants in memory marked as read-only so that the same bug would lead to a crash instead of surprising results. It's probably the most extreme example of undefined behavior due to breaking language rules that I've ever encountered.
I'm curious now if I would have seen the same result if I had made the 0 a PARAMETER (the Fortran keyword for a constant) instead of a literal.
Just to be clear, Fortran only "allows" you to do this in the sense that separate compilation generally makes it infeasible for the compiler to stop you. It's morally equivalent to the "undefined behavior" of C and C++ (strictly speaking, the program is ill-formed but does not require a diagnostic if I remember correctly).
Admin
Nah too generic "#define 4 5" would be a fix for this case. Gotta love macros.