How To Write Unmaintainable Code
/ writes "Roedy Green of Canadian Mind Products has written an essay entitled "How To Write Unmaintainable Code". Following his 54 tips, you too can guarantee job-security by becoming irreplaceable. If that weren't good enough, it's even available in Spanish. "
as a cs student, nothing inspires me more! job security rules!
I worked at the same web shop for 3 years while in college.
What started off as a no pay internship turned into a $60/hour job, mainly because my code was valuable and it would have been impossible for someone else to figure out what I did and how it worked.
Every time I mentioned other job offers, they just raised what they were paying me. It would have taken months for some fool to understand my code and do anything useful with it.
I decided to continue in grad. school and I feel kinda bad leaving them with an expensive mess of spaghetti. If they pay $100/hour I'll spend my winter break making it understandable.
Its karma, Kramer.
That had be laughing outloud! Being a web developer, I have often had to work with code that tried to do many, many thing. One web page would try to accomplish thirty different things, based solely upon the querystring parameters passed in. Ugh. Now there's job security! :)
I could not justify my existence if I were a turkey farmer. Would I terminate myself? Undoubtably, yes.
Writing unmaintainable code for job security is a Bad Idea (TM). Cuz guess what? You might end up the victim of your own practices -- and who's going to get fired when they've failed to figure out code they wrote a year ago? You. Don't do it. Maye you should work somewhere else where they know how much you're important and valuable to them, so you don't have to take such measures as to write bad code. And if you're going to get replaced so easily then maybe you were not worth your salt in the first place.- -----
-----------------------------------------
-----------------------------------------------
Unix _is_ user friendly, it's just particular about who its friends
He forgot one of my personal favorites. Make the code look like it isn't code. Such as
for(int i =0; i-->;)
in Java, C or C++.
Bad Command Or File Name
I tried to write unmaintainable, obfuscated code that would make be irreplaceable, but I failed. Do you think it had anything to do with my using Python? :)
Gates' Law: Every 18 months, the speed of software halves.
Checking out messy code after a few months with no documentation, I can't even understand my own damn code! That like, sucks and stuff.
-PovRayMan
----------
Check out my blackbox styles
I Quote from the essay .... Maintenance programmers, if somebody ever consulted them, would demand ways to hide the housekeeping details so they could see the forest for the trees. They would demand all sorts of shortcuts so they would not have to type so much and so they could see more of the program at once on the screen. They would complain loudly about the myriad petty time-wasting tasks the compilers demand of them.
This is precisely the reason VB is so popular for business apps. You have to really work hard to confuse matters sufficiently in a VB program so that a decent maintenance programmer can't figure it out.... although I could write my own list applicicable to Vb for my current project... My favorite: Make sure you have the same variable name to reference a database in several different classes in several different programs, but have it point to three different databases depending on which variable is in scope currently :)
DO NOT DISTURB THE SE
Personally once I write some code I want it to be maintainable enough so other people can contibute for I can move on with other things. I do not feel that my life consists of solely maintaining code, why not do something challenging? Rather then babysitting one of my past accomplishments. Why not take over the world?
Back in the good old days of DOS (and thus, 80x25 page size), I had a programmer in my team who followed the "all functions must fit on one page" rule...
Man, the number of times I wanted to kill that guy. We called him Anti-Whitespace.
Scarey though, how that page gave guidelines that I myself have been guilty of following too many times in the past. Is there a counter-page to that one, that gives guidelines (general purpose) that make it easier to work with other programmers?
; -- the corruption of government starts with its secrets. a truly free people keep no secrets. --
What about writing ugly code for an open source project? We are supposed to be supporting open source, and in the meantime this fool wants people to make code unreadable. The two won't go together, because if we want it to work WELL, we must comment it well, and not play tricks! Yea yea yea, i understand the job security stuff, and there are better ways to make yourself in demand. I'll take the article with only humor, but in no way would i take it seriously.
Berto
I hate it when members of my team write unmaintainable code. Frequently, when time's short or when people need help, I have to dive in, and I've found it difficult to get my bearings in code that I did the initial design for - difficult to see the forest for the trees, even when I planned out the forest.
Good practises in programming isn't just for academics; it's the epitome of professional code writing. A manager once tried to draw the definition of a hack and a real programmer by the completeness and bug-free state of their code. I think he's wrong. I think that a real hack writes code that no one can pick up. A real programmer writes code that anyone can pick up and fix or expand - whether it's complete at any one point or not.
--
--
There is no premature anti-fascism. -Ernest Hemingway
All you gotta do is write it in perl...
Good programming practices were invented to help _you_ the programmer produce bug free code. Perhaps this guy was a member of the Windows development team? (Sorry couldn't resist :-) Windows is crashing gotta go...
The stuff at the end about coding environments is very similar to what I have heard Smalltalkers describe as how a good Smalltalk environment works.
And of course anyone who wants to avoid accidentally using a few of those practices could be worse advised than to buy, read, and apply the concepts in a copy of Code Complete...
Cheers,
Ben
My usual seat in the cluetrain is at A HREF="http://pub4.ezboard.com/biwethey.ht
Now I write good code. Maintainable. Well commented. Meaningful variable names. Nothing fancy. I know what it's like to revisit my code ten years later.
There is a problem, though.
Nobody else seems able to maintain my code. They just can't understand it.
Despite high-level pseudo-code algorithm descriptions, threaded comments, good up to date written documentation, they just can't wrap their tiny little heads around how I do things.
I can go back to something I wrote 15 years ago and fix problems without generating new ones. My code is robust enought that I can shovel out a few thousand lines and jam in another 10,000 lines, test it for a day or two and release it... and get no bug reports for another 5 years. I consider this to be maintainable code!
Go ahead... break all the rules suggested in the article. You may still produce code that other, lesser programmers simply can't cope with. The code is an expression from the mind of the person who wrote it... and sometimes writing to the lowest common denominator simply isn't possible.
And then they blame you for writing unmaintainable code.
-Eldurbarn
Bah, I can tell you to do it much easier than that - use BASIC. >:)
--
Only one Microsoft joke so far? :) ouch, slashdot is slipping
What sense does that make? If a company wanted to fire an individual he probably sucked anyway! I mean, the market is flooded so much that there are currently more jobs than people around to fill them. So, if you are being fired - then you truly ARE a dumbass. Furthermore, imagine u got promoted (it happens), and then you had to deal with someone who fuq'd with their code so that no one can do anything with it. You would be screwed years of work and money. I dunno, jus way i feel. Ill stop now.
If I don't read my code for three days I get completely LOST. I'd have to either reread the whole thing (boRING!) or rewrite the whole sucker. I ABSOLUTELY cannot read other peoples code, I just don't understand what they're getting at. Who needs tips.
:P
It's not a philosohpical issue, it's one of practicality:
;-)
;-)
When (not if) you end up maintaining someone else's code, if the code has been written in a clean way, it can be a sure joy to work with. If not, you'll be cursing that programmer for eons.
(Lets keep Microsoft's API out of this ok
The REASON we want good clean code is so that _we CAN_ maintain it.
I have been in the position of looking at my own code 6 months, later, and gone "WTF?", and wasted lots of time trying to figure out just what the heck I did.
If I had just spent the extra time to begin with, later on I could of been more productive instead of wasting time re-engineering the damn thing.
Pay the piper up front and save time later, or be a "saving time" grinch, and find an expensive time bill later. Seems pretty obvious what "The Right Thing" to do is
Work smarter, not harder =P
Cheers
BTW, Steve McConnel has a great book: Code Complete.
The site appears to be slashdotted. If possible, can someone mirror it?
Byte had a feature entitled: "How to Fail at Software Development, Don't Communicate" it at a slightly higher level, but is just as useful.
--
"L'IT c'est moi!"
why not write the code in perl such that when the program starts it reads the code in and then executes from refrence to subs?
:)
(i've actually done that, and i understand what i do in my own code, but i'd like to see somebody else try to explain it
i seriously hope this page was intended as a joke
Need a Catering Connection
That is right. If you set out to do it in a sane way from the beginning you will very likely get the same task done more quickly than if you just hack out something on the fly and try to make it work. The maintainability and lower bug rate is a bonus on top of that.
Cheers,
Ben
My usual seat in the cluetrain is at A HREF="http://pub4.ezboard.com/biwethey.ht
They wrote a converter that digested the assembler and produced C code... about 4 lines of C for each line of assembler code.
So a math calculation that could easily be written in 1 line of C took 30 or 40 lines of assembler which converted into 120+ lines of C. (Stop screaming!)
Their converter did not put the original source line as a comment in the new source. (Now you may scream!)
Now I gotta maintain this pile of compost. I'm looking for another job.
-Eldurbarn
In naming functions, make heavy use of abstract words like it, everything, data, handle, stuff, do, routine, perform and the digits e.g. routineX48, PerformDataFunction, DoIt, HandleStuff and do_args_method.
He forgot "Thingy"! How can you forget "Thingy"? As in "Take the thingy passed in by the user, send it through the thingy, and return the thingy to the user" and "Merge the two thingies, extract the resultant thingy, discard the other thingy, you don't need it here, and then pass the thingy on to the next thingy."
I'm amused by how many posts here actually took this article seriously, seeing that it came from the "It's funny. Laugh." department. I suppose the phrase "It's funny. Laugh." should be taken in the imperative? :-)
mikre he sophia he tou Mikrosophou.
Looked great in preview, screwed when posted. The important flaw is on the last line; I think I can get this one right:
n ge(o-1,-1,-1)))
lambda x,y:(x<<8L)+y,map(ord,s)),e,n):chr(b>>8*i&255),ra
If you want to post <(<) or >(>) note that the preview form converts the char entities back to characters, and double check 'em.
24. Never document the units of measure of any variable, input, output or parameter. e.g. feet, metres, cartons. This is not so important in bean counting, but it is very important in engineering work. As a corollary, never document the units of measure of any conversion constants, or how the values were derived. It is mild cheating, but very effective, to salt the code with some incorrect units of measure in the comments. If you are feeling particularly malicious, make up your own unit of measure; name it after yourself or some obscure person and never define it. If somebody challenges you, tell them you did so that you could use integer rather than floating point arithmetic.
Looks like some Lockheed employee took this page too seriously.
(numbering might be wrong because i got it from the googlecache version, which has only 53 rules.
The shareholder is always right.
Ignore the conventions in Java for where to use upper case in variable and class names i.e. Classes start with upper case, variables with lower case, constants are all upper case, with internal words capitalised. After all, Sun does (e.g. instanceof vs isInstanceOf, Hashtable). Not to worry, the compiler won't even issue a warning to give you away. If your boss forces you to use the conventions, when there is any doubt about whether an internal word should be capitalised, avoid capitalising or make a random choice, e.g. use both inputFileName and outputfilename. You can of course drive your team members insane by inventing your own insanely complex naming conventions then berate others for not following them. The ultimate technique is to create as many variable names as possible that differ subtlely from each other only in case.
(e.g. instanceof vs isInstanceOf, Hashtable)
they are all valid w.r.t the conventions.
instanceof is an operator and a keyword hence should be all lowercase, isInstanceOf is a method name, hence should start with a lower case character and the rest of the words should be capatilized, and Hashtable is a class name hence every word should start with a capital. Hashtable is the only one you could argue, but I'd say that sun just think Hashtable is one compounded word in itself not two words that describe a class's function.
- Put all your code into a single function. (I've seen functions over 2000 lines in length.) After all, those nasty functions generate overhead on each call, and you want your code to be efficient right?
- Use hungarian notation for variables. Then instead of the overly verbose you have the nice and compact
- Don't indent your code uniformly. (This is a variation on #11 from the article.) Use Windoze or vi editors, with non-standard tab widths, for tabbing and indenting, which means that no one can see your code indented properly unless they use the same tools you use, with your same editing configuration.
- If using C or C++, don't use memory analysis tools like Purify, or its open source equivalents. After all, if you find your bugs too quickly, you might lose your job.
- On large projects with several programmers, make sure you change global header files that cause everybody else's code to break but yours. Do this late in the afternoon, so all hell breaks loose breaks right before people are going home, or late at night, so that everybody comes in fresh the next morning and wonders what the hell happened to the code that compiled perfectly when they left the day before. Either way, make sure you are not around when they find out! Otherwise you spare them the joy of figuring out what you changed, and why.
- Do really stupid stuff that you were taught from day 1 not to do, but everyone seems to do anyway: don't check for NULL, fix array sizes where you hardcode the max size everywhere, don't check for invalid or oversized input, etc.
- Use preprocessor macros. Lots of them. (I was actually on a project where someone suggested using cpp to define macros. For Java. Absolutely brilliant!) The key is to use a single macro for multiple statements, in effect using macros as function calls. Example: Notice the "hidden" use of external variables and functions. Remember, you want to avoid those expensive subroutine calls! And think of the joys of setting breakpoints and stepping through a debugger on that code!
- Don't use source code control. Or, use it, but never unlock or checkin your files. Feel free to steal locks on others, though.
And finally, one of my favorites, for all the young and aspiring hacker types out there:BONUS: With compact hungarian notation, you can become even more descriptive! So really the above becomes:
So much more descriptive information, all in the same amount of space. I've been on projects using this, and the sheer of joy of it cannot be accurately described in words.BONUS: Write extremely long lines of code, well over 80 characters per line.
BONUS: Do this right before a major deadline.
BONUS: Don't use the all uppercase convention in macro names; use the same naming convention as function calls. It's even more fun to debug when you have to spend time actually figuring out do_stuff() isn't even a function call!
MORE BONUS: Nest macro calls. Use the naming convention above.
EVEN MORE BONUS: Use macro calls as variables. Make sure the expanded macro makes function calls. Or uses other macros.
- Write code only for yourself. Assume no one will ever need to figure out how to use your code without poring through it in painstaking detail. Do not make it easy to use, interface with other code, or even compile. Include 30 caveats that would take you only a few minutes to fix, but you're just too lazy to. In other words, write as if no one will every look at or use your code, yet release it to everyone to look at and use. Defend your laziness, which is causing thousands of lost hours of work to others, by uttering useless and stupid "cool hacker" mantras like "Real Programmers don't write documentation" and "If it was hard to write, it should be hard to understand."
Phew. That little tirade made me feel good.----------
In a real emergency, we would have all fled in terror, and you would not have been notified.
Enjoy
Enjoy
Enjoy this
I miss-typed that url... Sorry...
You may laugh at this. I don't. We have a Fortran programmer that wrote a lot of legacy production code (for the Vax). I know fortran (at least up to fortran77) although I haven't written in this language for a long time. Some of the younger ppl trying to port the code to newer systems have had a miserable time. But, hey, no problem! This guy is going to port his code to run on a unix system and will rewrite in C. No wait, he decides that he will skip c and rewrite the code in a new language that he hears is all the rage; c++. Two years go by.
He gives up learning c++ and ports his code to c. Another two years go by. If you know fortran, then you know that character manipulation is a bitch. I check his code and realize that he does not know the rudimentary aspect of c. He has essentially rewritten the function atoi. yikes.
On a side note: Obscure variable names is nothing new. Take a look at old fortran code written for a system with a 8 character limit.
On another side note: Many, many moons ago in my 1st computer class (fortran), I wrote a program that used the variable names kitty, cat, meow, and woof. Kitty was the integer equivalent to cat, and meow was the integer equivalent to woof. The prof was not pleased despite my explanation of the brilliance of my choice of variable names.:)
Having spent most of this year climbing through other's crappily written legacy HTML, it was such a nice change to have to write my OWN code from scratch starting in October. :). As it is, I only "work" 5 hours out of the 8 I get paid for. After the last month, I "deserve" a break. :)
I was handing off pages to our PERL and PHP programmers, and they knew *exactly* where everything they had to do went, and why.
I only commented a few sections, but by gum they were the important ones.
Now I'm reusing 70% of the code to do 3 sections in one month, whereas the last section took a whole month to do.
If this continues, I'll work myself into a looong paid vacation
It'll be back to normal come December when the new stuff comes in, but right now, I'm enjoying the fruits of my labour.
Work smarter, not harder, neh?
Pope
It doesn't mean much now, it's built for the future.
To make your code understandable only to you, you do not need dozens of methods -- you need only 1. Apply password selection procedures to function names. Remember, a password is your dog's name, but with numbers in it (like your vet's phone number modulo its greatest common factor with 3) and written in h4x0r-speak.
-S
I have a cow-orker (we're both programmers) who once spent a day lauding the benefits of word wrap in editors, despite denials from the rest of us. Now I indent all of my code so that the lines just "happen" to wrap in such a way that it seems to nest wrong only for him. >:)
My mistake, posted too hastily it should have read more like.
//do stuff }
int i=0, x =5;
for(i=x; i-->0;) {
Bad Command Or File Name
I stumbled across this unmaintainable code article a long time ago (early this year, I think) while looking through the Java glossery, hosted at the same site. Why is it just being reported now?
Hey, I resent them mentioning these beauties! I love using nested ternaries. Strange no body else does, but I actually think they are quite usable.
Then again, I don't get much opportunity to use them these days...damn 4GL gibberish =)
The site was slashdotted, so this might be on it. What I like to do:
Name variables a series of l's (the letter) and 1's (the number). So you'll have:
ll1l1lll1
ll11ll1l1
1ll1l1l11
ll1111lll
and so on. Sure, if they use a font that clearly shows the difference, it's no fun. But it can be!
Good evening class. I'll be your exorcizer of idealistic nonsense for the evening. Just call me Bruce.
Now... preach all you like about how hard it'll be for the next guy, but like customizing my car or my house... I don't worry about what the next guy will think about my code. Do you care if the next owner of your car might not like it if you paint it red? Do you care if the next owner of your house disapproves of you converting the garage into a pool room? Heck no. Well, it's the same with me. I work for my own benefit, pleasure, and satisfaction. And to do that I've gotta do the best damn job I can at work. Otherwise; no money; no fun. This philosophy is reflected in my code as well. I've cranked out some godawful nasty kluges that confuse even me when I look at them a year later... but I got the job done, by the deadline, while some of the junior programmers seem to wanna rewrite everything to make it clean rather than break the nice design of the code. Feh. That's why they're junior programmers. They Just Don't Get It (tm). Their plan would send the company under. Stuff's gotta be done now and ship next week or there's no profit for the company and no salary for the programmers. Junior programmers always seem to be self-delusional with grand plans of redesigning everything. It never happens. Requirements change *ALL* *THE* *TIME*. Any static plan is doomed to fail. Once they realize this they make the transition from dreaming programmer to master hacker... or they can't keep up with the pace of real world business and disappear. You've got to be able to deal with old crusty projects written by long gone staff with more bags and bells and whistles and ornaments hanging off the side and kluged into it, written by more people you've never met, and you've got to be able to quickly and successfully hack more stuff into it and hack it and rehack it and change old stuff and keep it all running. Successful, on the fly, under the gun kluging is what distunguishes the Senior Programmers driving the big smog polluting, shitty mileage, comfy luxury cars into the front, covered parking space and getting the stock options and profit sharing and 401Ks from the idealist larval dreamers driving their small car becuase "it's good for the environment". Self-spirit-lifting-and-self justification-bull. Given the Big Bucks, you'd ditch that Civic for a gas guzzling SUV or Corvette too. So forget the dream. Getting a clean slate to build on is a rare event. 99% of all programming jobs you'll ever be hired for will be holding together someone else's code. Insane deadlines, getting the jump on the competition mid project, reamping of requirements (many times over), decision reversals by management, your latest self-gratifying achievement being abandoned and dumped because it's not needed anymore. These will all eventually break your spirits. On the plus side, once you realize this, you will be able to succeed and advance within your company or find it easy to get hired at the next comapny. because quick thinking master hackers who can do the magic again and again despite laying waste to the original vision and still keep on kluging and have it keep on working are what companies want. If you can do this, you will succeed. Getting back to the original question... do I obfuscate my code? It may certainly look that way to the idealist, but not so. True brilliance is messy. Remember the famous comment preceeding the task switching code in Unix... /* You are not expected to understand this */ But if you can, you'll be a god... or root... what's the difference again? Anyway, class dismissed.
Whom ever hired you should have provided more oversight. This is a common mistake in our industry, hiring students to write grownup code. There is a difference between being an adult and a child. You my dear boy are a child. Those of use who intend on making a career in software engineering behave like professionals, we do due diligence and write solid, maintainable code. If you end up in the industry for a while you would soon notice that it's a small world, and you develop a reputation.
With all the talk of job security (I realize most people are saying it with tongue-in-cheek), you'd think we were auto-assembly-line workers. If job security really is an issue for you, you must be a damn poor programmer to start with.
Now, having said that, the link in question was undoubtable funny, and I'm sure none among us can cast the first stone when it comes to the listed offenses, though I doubt most really do it for job security. Usually, its the insane deadline pressure or the dreaded feature creep.
a 210 line macro (in an 11,000 line .c file), ugh.
How many of the suggestions have you done:
None of them; all of my code is squeaky-clean
1-5
5-10
10-15
20-40
40-50
All of them, and proud of it.
3 + 6i of them
Hey, what about 16-19?
the MSDN sample code. They must use these rules as their "White Paper."
I got a few more:
- Routinely switch using null and non-null terminated strings. Bonus points for encoding in EBSDIC.
- Routinely change your array bases from 0 to 1 and back.
- One Word: LISP.
- Routinely use double-indirected pointers to undefined structures.
Okay, I'm done.
My god he's right! ^ is finally gonna do exponentation just like it fscking should!
The by line should read "Rob Malda." Rob wrote this as a guideline when working on Slash 0.4, and decided to publish it. He will be teaching a class on this at the Slashdot booth, located in the Linux Business Expo portion of Comdex on Friday.
#define FALSE ('-'-'-')
Fun and harmless. (Do all compilers evaluate numeric expressions at compile time?)
To clarify: "cow-orker" is an intentional misspelling of co-worker. I just like the way it sounds. I picked it up from the Dilbert List of the Day. It's not uncommon there.
You want to see unmaintainable code ?
Try and read Lisp Code.
I have seen Lisp code that the last 4 pages of the program were ")".And i am not kidding.
Tail recursion babyyyyyyyyyyyyy!!!!!!
BTW, google.com mirrors a lot of the web
I don't think anyone has commented on the final section of this essay yet, so I'd like to bring it up. We're all working in algorithms - essentially, pure ideas. If there were some way to boil your ideas into some universal language (structured data) then you've hit on that ideal: Truly Reusable Code.
I recall reading The Glass Bead Game recently and ended up thinking along these same lines then - perhaps this is where it starts? Its all about abstraction, after all... Go far enough and it all fits under the same umbrella.
Culture is more than commerce
Me and a friend of mine were writing a physics demo program as a class project a couple of years ago, and we made heavy use of picking insane names for classes and variables. As an example, one of the objects is a bond that obeys Hook's Law, but that needed a manager. So we called the manager a Pimp class. And the instanciation was myPimp. The function that told each bond to update itself, if I remember correctly, was actually called DoIt or something horrific like that. Then there were Erectangles that covered the surface of the solid we were generating... oh man, that was fun.
-S
Well I'm still a staunch opponent of using goto. Maybe goto makes you feel superior because you're using Microsoft's crown jewel of BASIC programming but unless you've got employers to impress Microsoft isn't everything.
at an ISP i used to work for a programmer got fired for writing such horrible code that was very difficult to understand (he had no formal coding training) i.e. if his program core dumped, he just wrote a wrapper to delete the core so it would keep running. eventually when we tried to update all of our machines we couldnt because his code was so limiting and no upgradable.
lesson learned: do not promote your own job security through obscurity. you'll get burnt in the end.
Naturally there's a version in Spanish. After all, one of the key rules is to always write your comments in a foreign language. They're there, they're up to date, they're helpfull but they're totally confusing to the poor bastard who winds up maintaining the system.
Ahh, the joys of multi-lingual development teams!
:)
I left my body to science, but I'm afraid they've turned it down...
Remember the old motto...
If you can't be replaced, you can't be promoted.
Don't leave your mind so open that your brain falls out. Don't close it so much that you cut off the blood.
Somebody suggested that training method when I was raising my first puppy. Now she's addicted to pepper sauce and beer. Dogs do not digest spicy foods well...
:)
"if you let someone get burned by their own bad habits, it is sometimes enough to break them of those habits."
And sometimes it just makes a big stink.
... if you think anyone would EVER be a victim of this practice. You think they want to rewrite the whole thing from scratch just to have the joy of firing you. I had a prof who told us his strategy when he worked as a programmer - leave the company so that they have hire you as a consultant at four times what you were making because you are the only one who can figure out your code. Brilliant! I used to write maintainable code. My boss once told me how great my coding and commenting was because anyone who came along later could figure it out. Then he retired. The next recession things slowed down, and I got cut because any newbie could read my code and build on it, while everyone else stayed around because they were invaluable - their coding was complex. I would tell people in interviews about my boss's comments on my code maintainability, AND THEY DIDN'T CARE. It's a moot point with employers, they don't have the vision to look ahead and value maintainable code, and they will throw you on the street the first chance they get if it doesn't hurt them. So I say screw them and make yourself invaluable.
It is apparent that your company is using a very ad hoc development process. It is UP TO YOU to work to change this, particularly if you're working with a lot of non-technical people. Try and convince your management to implement a formal development process. For each project, write a requirements document. Make several parties sign off on it. Make it so that any change to the requirements also has to be signed off by all parties. Whenever they requiest a new feature, simply tell them: "Adding feature x will take another 10 days. Either we can push the schedule back by 10 days, or we can remove feature y or feature z." This gives them a few choices, and if they insist that you implement both features, tell them it's impossible, and that they should know that as you've already set out the schedule and had them sign off on it.
As a responsible, professional software engineer, these are things you should be trying to do. If there is resistence to implementing a formal development process, you may have to negotiate a little bit. But ultimately, there is nothing unreasonable about doing business in a formal, well-defined manner. If they refuse to do things this way, make sure you remind them that there will be serious consequences (personally I would threaten to quit the job and work for a more reasonable employer, but that's not for everyone): bad software, missed deadlines, and maintenance hell. This gets you completely off the hook if anything goes wrong. And when things do go wrong, they'll think "he was right", and they'll realize just how good you really are.
If you want to be a successful software engineer, you need to adopt the attitude that you will NEVER be involved in a failed project (I had the chance to take an excellent course with Marshall Cline, of C++ FAQ fame, and this is one of the things he stressed most heavily and I see a lot of truth in it). You need to take a proactive approach. Take steps to ensure that management is doing things right, rather than simply sitting back and carrying out their instructions without saying a word. Of course, be diplomatic. This is part of a software engineer's job, IMHO. It is things like this that separate the men from the boys in the industry; the true software engineers from the coding monkeys. If you are a software engineer, it's your job to ensure that the company develops the best software possible, or at a more fundamental level, to minimize the time, money, and risk the company expends on the project. Doing that involves more than just coding.
In my experience, if you're developing large-scale software using an object oriented design, it's quite likely that if you designed the system well enough that your typical method will be one or two lines. Very few of your methods will be over 5 lines, and you will rarely need to put comments inside your methods because the code is so simple and obvious. This is the best way of develping software, IMHO, and when I was first exposed to object oriented programming and design patterns, and saw real code written like this, I was overwhelmed at the power of the paradigm.
these have been posted before, why can't you posters do a search before posting something?
This reminds me of the programming style of Dan Barrett. :) http://www-ccsl.cs.umass.edu/~barrett/bm/Viewer_Se ctions/Articles/77_ProgrammingTips
--
use INTERCAL. Perhaps the only programming language ever to actually use COME FROM.
Glückwünsche, haben Sie Slashdot ermordet, indem Sie zum korporativen Druck beugten und Subskriptionen einlei
Remember, FORTRAN is an acronym.
The last time I dealt with FORTRAN, I ported a massive lump of NASA code called QuickTOP (Quick Trajectory Optimizer) to the mac. I only modified the original code in two places. I let it do its initialization, then it would jump out to the GUI I wrote in Think C. The luser could set up all the mission parameters (what planet he needs to get to, what kind of propulsion is available, etc.) and then jump back into the FORTRAN code to run the sim.
The punchline is, when I had finished the port, the geriatric NASA guys asked me to translate the GUI code to FORTRAN, to make it... Wait for it...
... MORE MAINTAINABLE!
-jcr
The only title of honor that a tyrant can grant is "Enemy of the State."
Remember, FORTRAN is an acronym.
The last time I dealt with FORTRAN, I ported a massive lump of NASA code called QuickTOP (Quick Trajectory Optimizer) to the mac. I only modified the original code in two places. I let it do its initialization, then it would jump out to the GUI I wrote in Think C. The luser could set up all the mission parameters (what planet he needs to get to, what kind of propulsion is available, etc.) and then jump back into the FORTRAN code to run the sim.
The punchline is, when I had finished the port, the geriatric NASA guys asked me to translate the GUI code to FORTRAN, to make it... Wait for it...
... MORE MAINTAINABLE!
-jcr
The only title of honor that a tyrant can grant is "Enemy of the State."
Interesting article, Roedy, but you ought to be careful because I'm under the impression that a lot of the techniques you mention here have already been patented by a company in the Seattle region.
Adam:What kept you?
God:Rome wasn't built in a day
try this: .ne. 27) stop 'error'
ivar = 27
call sub (27)
if (ivar
.
.
.
subroutine sub (int)
int = 35
return
end
This delightful bit of coding overwrites the constant 27 with 35. It 'works' under some compilers I have used.
I actually find most Fortran programs easier to read than C programs. If course you can produce spaghetti with 'go to's but C allows things that have been outlawed by the Geneva Convention.
Mielipiteet omiani - Opinions personal, facts suspect.
Programmers know enough of the English language to comment? I guess if it was all abreviations and acronyms they could probably handle it. :)
me too. however, i was underwhelmed at the speed and resource usage.
"The more changes you can make between versions the better, you don't want users to become bored with the same old API or user interface year after year. Finally, if you can make this change without the users noticing, this is better still - it will keep them on their toes, and keep them from becoming complacent."
:-)
From this line, it becomes quite clear that they've started to document some of their common practices. They're not a monoply, they're just following their ISO 9001 certified business standard for programming
(Proof that ISO certification is just a piece of paper saying people do that they say they do).
---
--
Internet Explorer (n): Another bug -- that is, a feature that can't be turned off -- in Windows.
One other very general and very common method:
Start the implementation before the functionality and overall design are settled and agreed. This guarantees that different parts of the product (preferably the responsibilities of different independent contractors) will be constructed according to different tradeoffs and in extreme cases will be based on mutually inconsistent goals. This can confuse and impede even the rare maintainance programmer who is able to quickly pick up the overall purpose and structure of the product, and the style(s) of writing.
Note that this method is common in the Real World because it seldom has to be resorted to deliberately: it is a natural consequence of the additional (that is, changed) requirements typically imposed by paying customers in the middle of a project's implementation, or of a budget freeze that means that the first proof-of-concept prototype has to be extended into production rather than being thrown away in favour of doing the job properly, as the original project plan specified.
Sigh. After 20 years in the business I wish I were joking about this.
great post....so true it's scary
-- Went home. Had to feed the kids.
2) Create a search and replace procedure to use in vi!
3) Whenever you have to maintain the code, reverse your procedure.
%s/$employeeFirstName/$epfsnm
in reverse:
%s/$epfsnm/$employeeFirstName
4) put comments in an external file! HIDE IT!
--
I wrote the play & still own the script
Sheesh. :)
http://www.geocities.com/TimesSquare/Battlefield/3 691/unmaintain.htm
Clearly, the first priority is to produce on time. That makes all the sense in the world.
The second priority - for the products to be operational. So far so good.
The third, of course, is for all bugs and inefficiencies to be ironed out.
But shouldn't style come into play at some point? If the situation is code that has been, is being, and will be altered by a variety of people, shouldn't one feel at all obligated to lighten the load for the next guy?
Paint your car red - fine! But give the next guy the owner's manual, for heaven's sake!
In my opinion (which admittedly belongs to a lowly Undergrad), professional ethics dictate that the job be done to the utmost - salary and competition be damned!
What differentiates maintainable code from spaghetti code is not just whether or not the syntax of the language allows for obfuscated code, or if all of the variables and functions are documented and clearly named, if some code conventions are followed or if it has been run through a beautifier, but whether the code was written with a clearly thought-out and documented design.
If the programmer has actually taken the time to think about the data structures, the algorithms, and the classes(or program sections if you aren't using an OO language), then the code becomes truly understandable. This is not to say that you can then ignore good programming techniques -- they are still necessary -- but that documenting every function, variable and data structure in a program that is otherwise a crufty mess is pretty much a waste of effort. Try it sometime -- look at the source code for Perl, and have the perlguts man page and Gisle Aas's wonderful illustrated guide to Perl's internals handy, and you'll get the idea.
I've seen code in lots of languages that would be considered 'maintainable' if all it took was strictly following a convention, but in fact was frustratingly difficult to maintain because the programmer didn't have a clear design for the system.
A master was explaining the nature of Tao to one of his novices. "The Tao is embodied in all software -- regardless of how insignificant," said the master.
"Is Tao in a hand-held calculator?" asked the novice.
"It is," came the reply.
"Is the Tao in a video game?" continued the novice.
"It is even in a video game," said the master.
"And is the Tao in the DOS for a personal computer?"
The master coughed and shifted his position slightly. "The lesson is over for today," he said.
-- "The Tao of Programming"
bloody horrible piece of turd it is...
It fell to me to maintain a helpdesk system that a director of the company had written.
This guy wrote about 20,000 lines of code and all the variables were variations on the letter "t", eg t, tt, ttt, t1, tt1, t1t, etc.
He had the mistaken belief that he was a hotshot programmer. The rest of the real programmers knew that he was a clueless idiot.
In one report he had the calculation: ttt=t1+t2-((tt1*ttt1)/tt)+tttt1
He was very keen on squeezing as much code onto one line as he could too.
It took me 3 weeks to amend one report so that 1 extra item from the customer database could be displayed.
After this I wrote a suite of tools to reformat the guys code so that it was understandable, and pointed out the errors that he'd made. The same company director later made a small fortune selling my tools to the company that provided the database engine. I think that was his revenge.
I also knew one programmer that wrote an RPG system without using arrays, because he didn't realise you could do that sort of thing. Last I heard of him he was an engineer for Compaq.
Say you're programming CGIs in Perl using modules. Whatever you do, don't install new modules in the system-wide site library, because that could cause all kinds of trouble! Better to put them all in
Always keep a sapphire in your mind
I don't think anyone else has suggested this, but to make you program even more unmaintainable use special characters.
For instance MrC on a Mac will allow you to use one special character instead of two like opt-equal for not equal, opt-comma for less than or equal, or opt-period for greater than or equal. Now if you were to use this randomly, if someone else ever tried to port the program to a different platform using a compiler that didn't support these characters, it would be unpleasent to say the least. If you've done your job a maintainer would have to look at a bizzare character and guess what the correct symbol would be. Of course eventually a maintainer could figure out what character meant what. Even better depending on how the program was translated the symbol for less than or equal could be turned into just less than, making for a fun time debugging when things hit boundry conditions.
Impersonating Tycho from Penny Arcade since before there was a PA.
Nice two-dimensional language...
http://www.meta.demon.co.uk//zbefunge.html
from : http://users.ox.ac.uk/~univ0938/2dpl.html
Enjoy.
SO it looks like Microsoft decided to leak some of its coding secrets to the public.. At least there helping :),
Ah, don't forget the joy of trying to understand a set of several dozen objects when a procedure with maybe a couple of loops and arrays would suffice.
I've just got to leap in here.
We had a 30,000 line BASIC program that had been converted automatically to C - filled with "goto 3700" and "for (i_int=1;i_int
To cut a long story short, the company eventually went bankrupt.
I think the AWT designers probably had a good reason for designing the code that way..I'm not sure, but I'm guessing is that the classes used by the AWT are 'heavyweight' components that are provided by the OS, which might have restrictions on subclassing. Also Java does not support multiple inheritance, so inheriting from more than one class would be impossible..
The page was a Good read anyways! :)
I saw some code once that went something like:
int one;
int two;
int three;
...
int thirty;
...
...
one = big_long_math_expression_with_1_in;
two= same_big_long_expression_only_with_2_instead;
...
and on in the same vein for many pages. I don't remember what the code was meant to do, but it did it! I really really hope that the guy who wrote it knew about those nifty cut and paste things though.
Interleave your code with as much trace code and printfs as possible. This way even the expert maintainer really can't figure out what statement does something useful.
You could have replaced variable names with the names of your girlfriends. Saw that once in an accounting program. And subroutine names were their measurements and "attributes." Like moaner, shaker, twitcher, gasper.
Just hilarious. It's a great life if you don't have to sort out something like this.
label.set(selected->description);
title.set(selected->name);
description.set(selected->title);
Guikachu: Resource editor for PalmOS developers
Sure, this is #5:
5.In the interests of efficiency, avoid encapsulation. Callers of a method need all the external clues they can get to remind them how the method works inside.
This is an OLD item. I had seen this over a year ago.
Nothing new here. Come on guys lets put up CURRENT stuff. Not sutf that is over a YEAR old.
The Truth is a Virus!!!
My first *real* job was maintaining an inventory control system, on an IBM System/36, written in RPG.
In German!
It was bad enought that any comments were in German, and all accounting terms (stock on hand, out of order, balance) but RPG limited you to 6 or 8 character variable names. And it was someones bright idea that the first two characters were used to identify the program.
Then they used acroymns. Examples include GBKXA1 (always uppercase).
Above all that, RPG used indicators. These true/false 'flags' could be used to condition code, and 3 of these indicators could be concatenated on a single line.
Then you can set the indicators by placing it in columns from 60 to 65 (if I remember) based on the result field being zero, positive or negative.
Even better was the commenting function. RPG was (is) strictly column based. Place a * in column six and the line is a comment. How many times, when trying to work out what a program function was doing did I find that the code was in fact commented out.
Missing rule? Carefully hide open and close comment tags in the code
I was a good start to learn *what not to do* and the other guy's in the team taught me the basic's of maintanable code. Thankfully, I've forgotten most of it by now and work in the internet world where it seems obligatory to code in the most obtuse way as possible!!
All spelling mistakes are in my mind and are faithfully reproduced by my fingers
myArray[i]is not equivilent to i[myArray]
If they aren't, here is the proper conversion:
myArray[i] is equivilent to (i[myArray/sizeof(myArray)]+myArray%sizeof(i))
I think that is correct, correct me if I'm wrong.
I love C.
"Don't be irreplacable. If you can't be replaced, you can't be promoted."
This works. Trust me.
-- Ever notice that fast-burning fuse looks exactly the same as slow-burning fuse? I didn't... (Edgar Montrose)
If we take out your fancy dance around the subject, it becomes much simpler:
You're a thief.
You also deliberately sabatoged your employer's property. But, just like so many other criminals, you justify it to yourself with that babble.
I'm surprised I didn't see it in the previous comments (or perhaps I just missed it), but most of the obfuscation techinques mentioned above have been used in the IOCCC and commented in Don Libes' Obfuscated C and Other Mysteries (the book is currently out of print). I highly recommend it! :)
If you work in the realm of Internet development where development cycles are very short (a few weeks), IMHO you *have to* be thinking about the clarity amd maintainability of your code because usually you are not the only one who will touch that code. I just finished a project was a rewrite of an existing dynamic section of a website that took me two weeks to do. Most of the time was spent trying to understand the hacks on top of hacks on top of legacy code. (I'm talking about code that's 3 months old) This was a very frustrating experience. In a rapid devlopment environment a clear methodology is extremely helpful to avoiding the hours of ramp-up time that's necessary for someone who doesn't know your code to modify or add to it. -K
This article is a good tongue-in-cheek bit of humour, and i love a laugh, but i sensed that it was a little bit more than this.
When i was a kid learning basic, and was new to programming (12 years ago), i had this mentality. The mentality quickly dropped when i started having to maintain and design real projects. I very quickly learnt that there's nothing clever in making code that's hard to read.
My goals have always been development time, and execution efficiently. I've found that it's very easy to write a program that's fast and easy to read. If a piece of code is easy to read, then it's easy to debug. If you are wasting energies on making code that's hard to read, then it can't be good code, and therefore a good program. If it's not a good program, then how is that going to make you look as a programmer?. How does this improve your job security?.
In my experience, fantasies like these are often shared by newbies, or people who aren't very good at it. If this article has inspired you to become a "bush mechanic" style coder, then you shouldn't be in the game. You'd be better leaving the field and giving somebody else who is more gifted than you a go.
Why? Because that's what everyone's doing, at which point they bitch and moan about how their Fortran, Basic, and Cobol programmers can't understand the C++, Perl, and Java code you've written.
Funny thing.
They sometimes even have the unbridled audacity and incredible stupidity to demand that you convert your code to look like the languages that the "maintenance programmers" understand. I've never come up with a better answer than to suggest that people run very far, very fast from this all to prevalent mentality. The world is a strange place.
Vovida, OS VoIP
Beer recipe: free! #Source
Cold pints: $2 #Product
Vovida, OS VoIP
Beer recipe: free! #Source
Cold pints: $2 #Product
I think people are taking this way too seriously. Seems to me to be just a light-hearted look at programming, with much sarcasm, not actual advice on how to keep your job.
Maintainable code, aah, what exactly constitutes maintainable code?? Let us ponder, to those of use writing "C", we all "think" we know what this is, but, do we as programmers really ever think about this unless we are under the gun to figure out why this bit was flipped? Most of the really good programmers I have worked with don't write complex or unmaintainable code on purpose, this usually happens because we as a group are pretty lazy. Why write 10 lines of code when you can write 1 or two ? Perception also figures into this. For my money, there is no unmaintable code. Any good programmer can figure out whatever he/she wants, "what's printf/display for anyway". Now, before I get flamed, let me say that I have seen poor code, but - this is usually a factor of education, not intention. I usually hear this complaint from newbies/converts who suddenly find out that the computing world is complex and they may have to actually think for themselves. Ask yourself, are you complaining because this is a pain in the "xss" or because you don't know how to fix/implement your problem. If it's door number one, hey ding dong, your getting paid big bucks ain't ya?? Or door number two - shutup and learn you whiner!!
Confusion to the Masses
Most obviously obfuscated code is produced by relative newbies who don't know what all the features of a language are for (e.g. case conditionals implemented as loops etc.) It never looks professional to code this way.
And, after you've seen a few thousand modules done this way, you can pretty much burn through them; it's actually kind of fun, like doing a puzzle.
The evil done by obfuscated code is nothing compared to the evil done by obfuscated architectures. Any power you give somebody can be used for good or evil, and the power you have when designing in architectural dimensions (like class hierarchies or APIs) is both greater and more subtle. Example: DDE. Real world projects include not only bits of code, but class hierarchies, databases, file formats, external interfaces etc. You can write code as limpidly as Kernighan and Ritchie, but still end up with a system that is totally unmaintainable by anybody but you. Furthermore, it will be utterly unclear to anyone whether this was deliberate, or caused by technical constraints (i.e. things you must interface with), or is somehow tied up in the nature of the problem.
Write overly complicated code, and people will think you're an idiot. Design overly complicated systems and write beautiful code to solve the unnecessary problems you create, and they'll think you're a genius.
Post may contain irony: discontinue use if experiencing mood swings, nausea or elevated blood pressure.
Well I'm scared because I don't know if that is sarcasm or not. I guess I'm an idealist. I like to /design/ systems. Coding is just what you have to do to make your design concrete. A lot of people don't think this way. They think the code is the end, not the means. And hence you get nasty messy complex weak broken sorry ass systems and you need more people to support them than if you actually designed it correctly the first time. Sometimes I have to work on a project and I have to hold myself back from slapping everybody and starting from the ground up...I just have to grit my teeth and get my hands dirty so I can fix the a symptom of a much larger problem. Computing is truly going to hell if the above was /not/ satire...
It's 10 PM. Do you know if you're un-American?
My previous employer had a HUGE Dos system.
:-)
Started in BASIC, went through an interpereter to C and still had bits of assembler for certian bits. Wow, this code SUCKED.
I didn't have much to do with it, but I did have to emulate some things it was doing in a new Windows system (ewww).
The best part was when I found out that 'S' was a global void *. Depending on the part of the program it was used for a half a dozen different types. The structured programmer in me had spazmotic fits, but I couldn't have the programmer killed cause he was the owner of the company.
Oh, there was also a global 's' which was declared as an int but used as a void *.
Oh well, back to my stupid Access project. How can anyone work in a language without pointers?
-- I'm omnipotent, I just don't care.
-- IANAEG - I am not an elder god.
My first job experience was to help port some old Fortran code, from a mainframe to a workstation, and from Fortran-77 to Fortran-90. There were revisions and comments dating back to 1983 (this was in 96-97)... (Aside: There's an age/revision level past which code should NOT be maintained, it should be rewritten)
All in all it was a great learning experience. I've developed an aversion to spaghetti since then.
Imagine if you will, a 2000+ line subroutine containing many a multi-level if-else/for-do construct, from the depths of which conditional computed GOTO statements jumped into the middle of another multi-level for-do/if-else loop. Intercal was never more fun.
The true kick of the experience was that it was to be a code port. Not a rewrite. Not even a little. A straight port, so the original developers wouldn't have to figure out any new logic. Feh!
-- What you do today will cost you a day of your life.
You're correct. Use VB if you want unmaintainable code. But use Perl if you want _completely_ unmaintainable, horrible looking code.
(Don't laugh. I found this in real code. I found this in real code that had been cloned into 30 different files.)
In naming functions, make heavy use of abstract words like it, everything, data, handle, stuff, do, routine, perform and the digits e.g. routineX48, PerformDataFunction, DoIt, HandleStuff and do_args_method.
Oh, and a great way to avoid long functions is to break them apart like this:
(more real code.)
The cake is a pie
For god's sake, learn some lessons about maintanability.
Always use the least appropriate language for the job at hand. Use C or C++ for parsing simple text files. Write huge applications in Perl. Use Bourne shell script to create a GUI framework. The opportunities for turning a small programming project into a lifelong commitment are endless here.
Another axiom to this rule is learn an obscure general purpose language and write everything in that. Your employers will have such a hard time finding experienced help, you should be able to demand a daily salary increase.
the growth in cynicism and rebellion has not been without cause
If you can rewrite this kind of tough-math-intensive software, you'll become both a hero and a legend.
I'm working on a project now where I see a much better way to do something than what I wrote up in the design spec. But I'm changing the design spec only slightly, and that in order to simplify my portion of the code in order to get the product out the door earlier (albeit at the cost of making cross-platform ports a bit harder), not to fix the ugliness.
- Been there, done that...
Damn right. This is why the smart 'uns go into the consulting biz.
When you're crushing a man's windpipe with your knee, you can be sure he will attempt to bite you.
In ANSI C, build your program around one core function that takes at least 17 arguments (Do Not use a structure). Do Not provide a prototype in the header file. Insert (not append) at least 3 arguments each time you upgrade the library.
I was on the receiving end of that library. I won't tell you where, just consider every completed telephone circuit a miracle.
The UNROLL macro you show there is a loop unroll like "Duff's Device". I'll explain why you'd want to do this while I talk about Duff's incarnation (because it's related but more interesting :).
Duff's Device was a contruct created by Tom Duff as a way of manually unrolling a for loop in a highly optimal way. The story goes that he was writing a multimedia application and noticed through profiling that he was spending a lot of time in his tight loops. In these loops he was doing a simple operation (copying from a buffer to a port).
The problem was that for each copy, he would do a compare. so he came up with this code (Tom Duff is a professional and is it not recommended you try this at home):
send(to, from, count)
register short *to, *from;
register count;
{
register n=(count+7)/8;
switch(count%8){
case 0:do{*to = *from++;
case 7:*to = *from++;
case 6:*to = *from++;
case 5:*to = *from++;
case 4:*to = *from++;
case 3:*to = *from++;
case 2:*to = *from++;
case 1:*to = *from++;
}while(--n>0);
}
}
Yes it compiles. 7 compares are removed.
Modern optimizers have learned from Mr. Duff and will unroll loops for you (if you choose speed over size), so you no longer have to subject people to this kind of heinousness. It is notable though that the TIFF code does an op1 to every 8 times, so this construct may not be removable from the code where op1 isn't NOP.
For Tom Duff's commentary on Duff's Device, Go here
-no broken link
Some have claimed difficulty viewing this site and speculated on ./ism... it may be browserism and anticacheism. It will serve to kfm, Arena, lynx, and curl but sends my Quill empty content. And they all went through the same Squid.
I think you've missed the whole point of Hungarian notation. Those examples you used were quite contrived (and if they did actually exist in code, it is the coder's errror, not the convention).
HN is a good way to indicate the kind of variable, and it does not preclude meaningfull name. What is maxTypeCode? A string? An int pointer? Pointer to a user defined type? I don't know without scrolling back up to the declaration. is numLinePayments a signed or unsigned int? On the other hand, pszMaxTypeCode tells me instantly that it's a string and iNumLinePayments is signed.
Likewise, your iNmPt example illustrates braindead programmers, not the shortcomings of HN. It should have been called iNumLinePayments.
I think too many unix coders are frightened off from HN simply because it came from Microsoft. Don't be. Try out HN, and if you don't like it properly used, then don't use it.
A Government Is a Body of People, Usually Notably Ungoverned
Ha... found it. Quill sends a content-length header in the request, and the server thinks it's meant to limit the reply content. As I read HTTP/1.1, that's incorrect (and sending it with a GET may be incorrect, too. Bleah.)
Someone better tell Novell? Anyway, that's unlikely to be the cause of others' troubles.
void markle(MARKLAR marklar) {
MARKLAR* Marklar;
Marklar =
Markle(Marklar);
}
/* This takes the marklar, creates a marklar to it and then just uses Markle on the marklar that points to the marklar.*/
The first mistake I'd like to clear up, is the class title. Just because a programmer codes cleanly is no indication that his spirit has been broken. In fifteen years of programming (that's after Uni), I've noticed that source code is a fairly good indication of thought process. If the code is badly laid out or badly commented, it's a good bet the programmer didn't know what was going on -- he was just typing until things worked. (Or in some cases, he was consumed by his own cleverness.)
Source is an indication of one's own thought process. Unfortunately, when you're looking at the source of massive real world projects that spans years in creation, hacking, and rehacking, you're seeing the though processes of uncounted current and former programmers all jumbled together. It resembles the billions of dendrite strands in a living human brain. Pure spaghetti to the eye yet a functional masterpiece. Comments are just clutter. They are only useful to the programmer during the time he's initially developping a given module. After that no one updates comments because there's no time to. Fix the code first. Fix what the compiler ignores later. Of course, there will be no later, because when the code works, the boss sees you as "now free" to start implementing the next task. The programmers knew what they were doing. They just didn't have time to spoon feed that knowledge to you. If you want to know... there's the code. And, unimaginable as it may be, yes, sometimes you don't know why shuffling some piece of code around fixed things... but it did. And sometimes that's good enough. The customer has already been screaming for a week. He needs something to work now. Think before you flame. The alternative would cost the customer account all together. Bottom line, remember? Onward.
His second mistake was the car/house analogy. He's absolutely correct that we don't/shouldn't care what he does to his Rumpus Room or '66 Muscle Car. Unfortunately, the software we're talking about is not a private Rumpus Room. It's a bridge ... on a heavily used interstate. If a bolt starts to work loose, the DOT wants to find it, pull out a standard crescent wrench and tighten it up. They do not want to spend two weeks admiring the "artistry" of how the original bridgemaker met the schedule by using a one-of-a-kind unlocatable tool to attach two pieces.
Well, this seems to agree despite it accusing me of a "mistake". This is right. "Get it done". Fix the bug and move on. Did you scrawl a note on the steel girder next to the bolt explaining why it was replaced and update the blueprints to reflect that this bolt may be of a different thread width, alloy makeup, age, etc.? Hell no. the next guy will not analyze why your bolt is failing 50 years later. He'll just tigten it or grab another bolt out of his truck from another bridge and ram it in there. He will not design, cast, and forge a new bolt from slag. Moving on...
He is correct that, once you leave Uni, you will find that practice wins out over theory. Alot of Software Engineering theories are (at worst) claptrap, or (at best) a germ of a good idea wrapped in layers of claptrap.
The problem with the theories is that they assume the problem is fully or even partially defined beforehand. They neglect design changes, feature requests, outright reversals of the desired goal mid-project. The user will change what he wants once he sees the work in progress. Software engineering theories that cannot tolerate continual changes and bashing are claptrap. What's more important is that SWE theories all assume you're starting from scratch. WTF?! No SWE theories even exist that have a pre-existing, hacked many times over, messy pile of code as their starting point. So much for the textbook solutions. Hacking new stuff into a crusty hulk is a skill, sadly, that schools don't teach. And which do the graduates end up dealing with more often? Clean slates or dozen/hundred/thousand man-year horrors that gotta keep chuging along?
This, however, does not excuse you from writing clean code. Document tricky solutions. If you don't document tricky solutions, people will correctly assume you didn't really understand what you were doing.
"If it was hard to write, it should be hard to understand.", words from Mel, one of my few successful graduates. A good kid. Did well for himself. Time. Time. Time. There's just not enough of it to splurge on comments. And comments that are out of date with the code are WORSE and far more DANGEROUS than no comments at all. Do you KNOW that you'll have time for adding/adjusting comments after the new feature or bug fix ships? Heck no. And you certainly can't do it beforehand, because you haven't written the code yet, or may get pulled off onto a more important project. Your comments will confuse. Even if you do have spare time, don't do it! The next programmer will modify your function and not update your comments. Now, if bugs appear, they'll be your fault and your screw up! And the bug fixer (a third person now) will be addled by your now eroneous comments. Comments are just too risky. The code is always true and never lies. Tell a man how you built a frob and he'll understand frobs. Now give him a modified frob, and he'll break it because his instructions are wrong. Teach a man how to reverse engineer, and he'll be able to figure out how anything works without relying on out of date schematics (comments) confusing him.
Also, arrogance will come back to bite you. I once saw a programmer publicly (and sweetly) toasted because the comment
/* Don't change this, because you're too stupid to understand it */
The toasting came from another engineer because the code which followed that comment was not only convoluted, but it contained an error.
The other engineer has no sense of humor. Besides, I'm not sure who's really being arrogant here. The other engineer is wasting his time being smug and court-marshalling people and boosting his own ego instead of fixing the damn bug and getting on with work. Besides, there's nothing wrong with arrogance so long as you're getting the job done. I ignore comments from most of management. Let the functional code be my judge. Bugs happen. No need to get all bent out of shape over it. Just fix it and move on. What's the employee's total track record look like? That's what matters to me. And that's what matters to the boss.
Thank you class. Your homework assignment for next week is to realize three things:
1.There is a balance between deadlines and good code.
2.There is a balance between "artistic freedom" and uniform standards.
3.How well you strike these two balances determines your overall worth as a programmer (in both a spiritual and a monetary sense).
Forget that:
(1) You have the best looking code but the poorest reputation for meeting deliveries, so no one will want to deal with you.
(2) Art is irrelevant. Standards schmandards. Code that works is beautiful.
(3) How your boss and the business world determines your worth as a programmer is of greater importance. Working code, on time gets more smiles and raises and promotions than "good" programmers still fscking with last month's task while the customer has long since jumped ship to your competitor. Spiritual worth is a seperate and unrelated issue. And I'll say it again because it bears repeating: Quick thinking master hackers who can do the magic again and again despite laying waste to the original vision and still keep on kluging and have it keep on working are what companies want. If you can do this, you will succeed.
Have a good holiday. Class dismissed.
Indeed. And to you all.
The trouble is, when you build a bridge with your crappy "get-it-done-at-all-costs" mentality. The problem is that the bridge collapses while the DOT is trying to figure out how to tighten the damn bolt. Since you were so clever in your construction that even that simple operation is a complicated mess.
Of course, after the bridge collapses, you point your finger at the folks who where driving over it, or at the poor DOT engineers who were trying to untangle your mess.
Read my homework assignment. You might benefit from it. Certainly, you can't spend all the project time waving your hands and philosophizing about how to do the task. But setting your thick ass down in a chair typing until something works is almost as bad. The keyword here is balance. If you can't write code that is easily maintained, then you can't write code . But I suspect you're tenured now and will never learn. You'll continue using the constant 100 in your code instead of taking 3 seconds to #define FOOBAR_ARRAY_SIZE 100
Don't worry though. One of us truly talented "Junior Programmers" will always be there to clean up the mess you left behind.
It's a thankless job. But if we didn't do it, there'd be no bridges.
The "arrogant" coder was seen as a "golden boy", by management, but a fairly incompetant jerk by anyone who could code. He basically pulled his "get it done" act to impress managers and get ahead. That's why his comeuppance was so sweet. As far as I know, he still thinks he's God's gift to computers.
As for the deadlines, I've spent the past 15 years working with deadlines. You can blame clueless bosses if it makes you feel better. But I've found that you usually can point out why something needs to be delayed or reduced in scope. Be honest and firm. It works for me, but YMMV.
As for the code which resembles dendrites ... I've seen that stuff. Have you ever taken two seconds to wonder how it got like that? No, I don't suppose you have. I'm not idealogical enough to think that code will always be pure and chaste, but well-designed code will stand up to enhancements and expansions better. Sure some changes can turn the code sloppy over time. But there is no reason for addition of related features and bug fixes to turn a program into a map of the "Brain that Wouldn't Die".
Reread my bridge example. You've missed the point -- which was the DOT guys can't fix the loose bolt before the bridge collapses because the joint looks like nothing else. Sure in a pinch they can break out an I-beam and a couple of props. But if you had properly designed the joint, then their fix is much quicker and much safer.
Anonymous Kev
PS: I didn't realize I was flaming you. My goal was to use your format to present my opposing view. Now what were you saying about needing a sense of humor?
I swear I am not making any of this up.
That PHB got promoted three more times before he retired.
> What is maxTypeCode? A string? An int pointer? Pointer to a user defined type?
Unless you're writing a device driver, WHO CARES? If you stick to the functional interface used for creating, setting, and passing that value, the type of maxTypeCode is OPAQUE. It's called ABSTRACTION, something we learn when we stop having to know encode our routines for sizeof().
I've finally had it: until slashdot gets article moderation, I am not coming back.
Is that you get chained to your code. The volume of documentation on my code is bigger than my code, because I can hand it to someone, say "this is all you need to know", and leave that code behind. Forever. On to bigger and better projects.
I've finally had it: until slashdot gets article moderation, I am not coming back.
Not to mention "widget" and "gizmo". These along with "thingy" were my favorite object/function/variable names in college.
If a problemset was hard to do, it should be hard to grade! ;)
----------------------------------------------
-*- Any technology indistinguishable from magic is insufficiently advanced -*-
quick quiz: from memory, tell me what these HN prefixes mean (answers here. no peaking, and no searching msdn)
anyway, im sure i could dredge up more examples. one can verify my answers by whipping out msdn, searching for "Hungarian Notation", and reading the handful of docs that come up.
But its interesting to note how many items on the list can't be done in Ada. By my accounting 11 items of the 55 (20%!) aren't an issue in Ada:
- 12 (no optional block delimiters)
- 14 (case insensitive)
- 16 (literals are not type-designated in this way)
- 17 (case insensitive)
- 23 (passing mode is explicitly stated in interface)
- 27 (arrays are not pointers, and pointer arithmetic is not allowed)
- 37 (names must be unique within the same scope)
- 44 (named notation insulates clients from parameter order)
- 48 (no macro preprocessor)
- 52 (no macro preprocessor)
- 53 (only one way to declare arrays)
- 54 (its tough to do this conversion in any way other than the straightforward one)
I guess one good addition would be:Seriously, how many programmers have had to deal with some lame-ass coding standards designed by a committee that obviously hadn't done any real coding in years? My personal favorite is to avoid the use of any and all loop jumps, like break or continue. How is it easier to read 8 levels of nesting, with all sorts of redundant comparisons and operations, when the whole thing could be fixed with a simple return? This is the type of thing that kills big projects. Ever had a code review, where nobody has time to look at the actual content and purpose of the code, so they just start rigorously enforcing these arbitrary coding conventions? Inevitably, the code gets completely rewritten for a bug fix (with no code review) and the standards go out the window.
A lot of people have commented about changing requirements causing redesigns. My complaint is that too many people (managers) refuse to see beyond the current requirements. Sometimes, you just know that the customer is going to want something eventually, so you want to spend a little extra time up-front preparing for it. But unfortunately you get forced in to doing things the quickest way, and then it's too expensive to add the features that would really be useful.
It sucks, but usually you need to be first to win the market. But if you look at most products that were first to market, they sell well for a while, but eventually the competitors overtake them. It's usually because they didn't plan ahead in the original implementation, and are now left with unmaintainable code that needs to be completely rewritten. There are too many examples to cite..
I sent the author this email to get the mistakes fixed: Subject: Suggested amendments to "How To Write Unmaintainable Code" Roedy, I loved your "How To Write Unmaintainable Code"! It was all dead-on, great advice, especially for those new to programming! All of it, that is, except for the latter parts of points #10 and #25. The latter halves of points #10 and #25 are marred by gratuitous USA-bashing which is not only factually inaccurate, but lower the tone of the points made. I'll address the inaccuracies: Point #10: (...) Consider variant spellings as a variant on the ploy, e.g. mixing International colour, with American color and dude-speak kulerz. (...) Comment: What International Standard are you talking about? The only thing noteworthy about "colour" is that it's the spelling used in Great Britain and all its colonies. It's no more of a spelling standard than Queen Elizabeth's face appearing on all bills is a currency standard. Furthermore, there are other words with variant spellings/forms that are commonly used within the same country. Example: Muslim/Moslem, lit/lighted, etc. Perhaps you should change that part of #10 to say that a programmer should stick to the same spelling/form that already appears in the code, for consistency's sake. Another thing to add would be that variant spellings of options should be accepted as input by a program. Example: a program that accepts "-color" as a command-line option should also accept "-colour". Variant spellings/forms will always be with us, and we just have to accept it, unless, of course, our aim is to simply piss-off other groups of people. Furthermore, if "color" vs. "colour" strikes you as too hard to handle, what do you think about Java making it possible for Indian programmers to name their variables, classes, and methods in Hindi? Your implicit assumption in #10 is that all code is going to be written in English. Perhaps you should make this explicit. Point #25: In engineering work there are two ways to code. One is to convert all inputs to S.I. (metric) units of measure, then do your calculations then convert back to various civil units of measure for output. The other is to maintain the various mixed measure systems throughout. Always choose the second. It's the American way! Comment: This point is just flat-out wrong and ought to be deleted from the article. The S.I. units, athough they comprise an excellent system, are certainly not the only system of units used. (Many physics calculations, for example, are much more cleanly expressed using energy units of electron-volts, or eV, rather than Joules.) If, for whatever reason, other units are used, it makes no sense at all to convert them to S.I. for the purpose of making an intermediate calculation. This pointless conversion simply obscures what's going on, causes precision loss, and makes the program run slower. God forbid it should take place inside a loop! The important thing is to document the units used for each variable, as you pointed out in point #24. I sincerely hope you will address these inaccuracies so that not a single flaw remains in your otherwise excellent on-line article.
Nasty article. So much chumpness and gravity that I gained twenty pounds of angst just reading it. In the end, the karmic boot will jam itelf up your ass is you follow the path of confusion. The simplest path is always the best and is usually the easiest. True programming geniuses don't rely on ninja smokebombs, fake teach or plastic vomit to keep their jobs. Get thee to a nunnery! J Carter Bermuda
In any case, your point is well taken, that Hungarian notation is not as obfuscated as my not-so-contrived example makes out. My only experience with it however was on this one project which did have such convoluted examples. Hopefully my example speaks to the broader issue of useful variable naming, not just Hungarian notation.
----------
In a real emergency, we would have all fled in terror, and you would not have been notified.
I cannot possibly be expected to read all of these comments.
The makings of some of the worst programming problems in the world in one little web page. I propose that you try these suggestions with Scheme (never heard of it? Try appending a .org):
I think I had better stop it at 10; the fun could go on, but it doesn't. Just another little morsel: Scheme comments are semicolons. Play tricks on people who are used to shell scripts. And there are some important cases where #'s are legal, specifically to quote an atomic (bunch of characters put together that isn't a string) element that includes spaces. Tada! Your comments look like code, and your code looks like comments!
I use Scheme how it was intended to be used: elegantly and flexibly. But there is a lot of room for error--Exploit it!
Kenneth Arnold
PS - Scheme really is a neat language, if you have enough time to learn it. It's a lot like Perl in that it's great for parsing stuff, but it's more flexible, for example, the function rules are greatly relaxed (see #1.)
True, Hungarian notation isn't useful in the cases where you "don't care" about the type. That's because those cases are far fewer than you seem to indicate in your post.
HN is about preventing problems that occur when you interface variables of similar-but-different types. It helps you keep track of which are of which kind, when the compiler can't tell the difference.
For instance, you might use a notation to indicate that your variable is a 0-based index or a 1-based index. (Another more common example is the "Last" versus "Limit" distinction) This is not something the compiler can know (yet) unless you decide to use completely incompatible types, which typically introduces more problems than it solves. It definitely creates a potential for problems when someday you try to use a 0-based with a 1-based and your compiler doesn't complain.
So yes, you can easily set and create any value without knowing its type. But you're wrong about "pass" because you can't use it as a parameter without knowing *some* type information. Sometimes the *some* is within the means of the compiler, sometimes not.
Presto
One of the better points I've seen in the posts is something to the tune of "It doesn't matter how well you write your code if the person that comes behind you just doesn't get it", which results in the writer getting stuck with the code.
:)
:)
The reverse is true, in that poorly written code can be understood by someone else, and that someone gets stuck with the code (and job security) instead of the writer. And right now, that someone else is me.
Note to sucky coders: A major part of your retirement planning should include recruiting bag-holders to maintain the code when you leave.
I loved doin this back in high school to mess with my cs teacher... 15 variables of different lenghts of underscores. Worked in pascal... works in C++ :) int _ = 0; int ___=0; int __ = _++; _ = __ + _ - ___ etc... if the font is weird, all those underscores connect :)
You mean you did what the Autoloader and Selfloader do as well?
-- Abigail
It makes all the difference in the world if you're a code *maintainer*, as this whole article is about. If you write code only for yourself, then you can use any coding standard you want. But then again, if you're only coding for yourself, why even release it :-)
A maintainer DOES NOT want to flip up to the top of the header files each and every time he runs across a variable to find out what it is. If a bug is signed versus unsigned related, "maxTypeCode" doesn't help at all. But an "uMaxTypeCode = -3" sticks out like a sore thumb.
A Government Is a Body of People, Usually Notably Ungoverned
Answers are: integer, pointer (to something), char, float, and who cares :-)
Without looking anything up, I think mps is a Microsoft/Windows/vc++ specific prefix. I do recall that "h" was for handle, and when you're using handles for *everything* in windows programming, it makes it much easier to distinguish between ints, files and handles.
But just like the guy who avoided all whitespace because he was following the rule to keep all functions one page in length, you can overdo HN. The basic idea is to use easy to remember mnemonics with prefix notation. Using "intEmployee" and "dblSalary" is equally useful.
A Government Is a Body of People, Usually Notably Ungoverned
>Oh well, lets leave this one to the archives of
:) For the most part, that is still the law in the U.S., but were old law by the time we separated.
.
Good idea, it's beaten to death. But one little note: I'm not talking about US employment law, but the Common Law of England
hawk, esq.
IMAO, HN was invented by someone who was too lazy to write a simple cross-referencer. Any bugs dealing with incompatible varible types should have been worked out long before a maintenance programmer gets hold of the code. While some may complain about having to scroll up to the top of the routine to check a variable's type, what am I supposed to do with someone who uses their own personal "Hungarian" notation? Like (my favorite) the person who bases their notation on their redefinition of the standard C types:
#define UINT unsigned short
UINT uiCounter;
And what the hell's up with "lpsz" anyway? Long Pointer[1] to String, Zero-terminated -- what other kinds do you work with? Sure there are fixed-length strings, but do you then feel compelled to prefix them "lpsf30" to indicate a Long Pointer to String Fixed at 30 characters? Why not just prefix with "s" for String and special-case the exceptions? Not that I care; I tend to use string descriptors & my own string library to prevent buffer overruns & other associated problems -- but I imagine lots of people do that.
[1] And don't get me started on Long Pointers! If you're using a proper (non-segmented) CPU, you don't have to waste time considering pointer size and memory models...
Just junk food for thought...
"HN was invented by someone who was too lazy to write a simple cross-referencer."
Do you know who you're talking about?
"If you're using a proper (non-segmented) CPU, you don't have to waste time considering pointer size and memory models..."
It must be nice to pick and choose the assignments your employer gives to you.
A Government Is a Body of People, Usually Notably Ungoverned
yeah probably
i didn't know anybody was as twisted as me.....
you can save a lot of work by being twisted though... rather than a bunch of if thens when you get something from a server to call a function named one of the parameters, just call &{$func{$param}} (after checking if it exists....)
Need a Catering Connection
Your drivel about how victimized you are makes me gag. If you agree to do something, do it. If you don't think you're being paid enough to do a new task that wasn't in your contract, renegotiate your contract.
Having a tech support rep do some VBA coding in Excel doesn't sound to me like they're asking for much. I happily did some VBA for Excel back when I was a TS rep, just for the additional challenge, and it ultimately led me to big bucks as a full-time C++ & Perl programmer for a different company. Still, you were free to choose, so you could have renegotiated or just refused. And none of that "no, I wasn't free, they would have fired me" nonsense. You could just as easily have fired them (gone to work for someone else) for refusing *your* demands. If they weren't willing to renegotiate, then maybe the value of this VBA work you did wasn't as great in their minds as it apparently was in yours.
Do what you say you'll do, or don't say you'll do it. Negotiate up front, and deliver slightly more than you promise, and the world can be yours, especially if you have valuable computer skills. If the other party asks you to do more than the contract specified, decide whether to give it, or charge for it, or otherwise renegotiate as you feel appropriate, but do so up front. If they don't deliver on their end, don't do business with them, and learn how to structure a contract so as to minimize such risks in the future.
Or, walk around whining about how victimized you are by Business and Corporations, engaging in pathetic little acts of sabotage to secretly compensate in your own mind for what you are too wimpy to publicly negotiate, and you'll be a lackey forever -- and rightfully so.
The language has type information, don't be redundant by encoding it into the variable names. Any decent editor will tell you the types of the variables without having to "flip up to the top of the header files" and without mangling variable names.
Sumner
-- rage, rage against the dying of the light