Repeat after me... 04 Jul 2003
Global variables and objects
Oh, I thought I'd come up with a legit. scenario for declaring a couple of global string variables in some Lotusscript I've been working on. How wrong I was. Bad move, very very bad. I should have stuck with my original theory, that one should never use the buggers1. I'm not being a total stick in the mud, others seem to agree with me. For example, Andrew Pollack, who gave a very good talk on advanced Lotusscript techniques and approaches at The VIEW's techie conference in Amsterdam last October. In fact, whilst I'm on about this, here's a link to his presentation: Advanced Lotusscript - Performance & Reusability
The whys and wherefores of this dogmatic stance of mine I have also covered as part of a longer draft I sent to e-Pro magazine back in April. I don't know if that will see the light of day as an article though, so maybe I'll ask if I can reproduce it here someday.
Anyway, back to the code. Ironically, these particular string variables were supposed to help me identify erroneous code. I was using them to track Lsi_info details within a scheduled agent linked to two script libraries (containing thirteen separate routines between them). Much scope for calamity I'm sure you'll agree, and by jiminy I hit it: how can you possibly debug iffy code when your NotesLog doesn't even come close to reflecting reality (i.e. not giving the correct name of the buggy routines). Gah! I'm such a doofus. Keep your scope as tight as possible I say, unless you have a brain the size of Mars to remember everything that's changing.
Tchcoh. So, please feel free to weigh in with your own tales of silliness, if only to make me feel better.
A belated happy 4th to my readers in the US of A, and to everyone else, a good weekend!
1 - OK, disclaimer. I have been known to use globals for standard error messages / UI text and such. But they're always expressed as constants, so that's low-risk eh!
We have pretty strict rules about naming modulars/globals (all modulars are prefixed with an m, all globals with a g), how we declare them (together, in a clearly commented section close to the top of the Declarations section), whether there's _any_ chance that a library will ever be 'reusable' in another context where reliance on globals would break (eg. classes never rely on globals, they init with passed arguments), and apart from some of the 'common' modulars where experience has proven them safe, we encourage long, long, hard thinks before making anything else modular/global.
We have reams more 'standards' (some rather unorthodox) regarding things like scope of constants, public/private routines, and so on, but in general I agree with you - the scope should always be as narrow as possible.
(and yes, most of this has been the result of very painful experience :-)Colin Pretorius#
So why I did this with the three string vars I don't know. It must have been a bad morning / low coffee rations ;-) Ben Poole#
As an aside, I really don't like cutting/pasting routines, and hardly ever do it. The occasional once-off agent might make sense, but 9 times out of 10 it's likely to become a maintenance nightmare (hmm, does this agent use the foo() before Joe added the frob fix?) I prefer for the routine to be moved to helper libraries anyway - where the interface and behaviour is clearly documented, by its nature globals/modulars won't be used, and the process of making it more 'public' means that it's been (re)designed for generality anyway.Colin Pretorius#
I'd be full of b.s. though -- much as I'd like to, I've never actually assembled all those helper functions into a single library.
Oh well. Its a case of the cobbler's kids having no shoes I think.Andrew Pollack#
I just did a google search on "Tchcoh" and it returned me 2 hits, one to this site and one to macfora.com, to a post written by you! Don't you think you owe it to your many avid readers to do one of your funky popup definitions for this (IMHO) underused expression :-)
(looking forward to a few pints with you on Thursday!)Spikey#
(HINT: "Gah" has become my ejaculation of choice over "Tchcoh" but the latter still holds a place in my heart).Ben Poole#
For the other things (current db, etc.) I generally decare it for the current scope only. If I need to "do" something to it, then I delcare it in the "hosting" code (such as the Initialize of the agent), and then pass it as a parameter on the function/sub. Same thing applies for "new" values that the function produces - I always pass an "empty" var in as a param, and get the value back from the function on that var. Functions always return error codes themselves, and pass values/objects in and out on the parameters.
So, I am like the rest of the folks here - Globals are in the same ilk as GOTO ;)
RockRock#
LibbySheepish Libby#
I agree with the rules, I've also been burned by the kind of thing that happened to Ben - I think I'm just a bit more comfortable about breaking them in certain (limited) situations. What gives me more confidence about it is making sure that if I do, it's documented so that other coders know what I've done, and won't have any nasty surprises or head-scratchers induced by what I've done. I think working in a company with a single batch of apps and standards makes this easier. If I was doing a consulting gig, I wouldn't have that 'familiarity' luxury and would steer clear.
As for gotos, no arguments from me there. Then again, Dijkstra also said that anthropomorphising computers is a sign of professional immaturity, but if you can't say things like 'compile, you *%$#@!' then what's the point?Colin Pretorius#
you, er, rock!
btw, THAT is the kind of stuff we need in best practices sessions. things that the help just doesn't tell you (or does it?), that the notessession is the same one whether you declare 8 times or once.jonvon#
(12) … as for you Colin, LOL ! You've made some great points that brook little argument. Your bit about anthropomorphising computers is hilarious: how many times do I say "Oooh, you fu&*!er" to my StinkPad in one day? Scary.
Bad coder, BAD coder…Ben Poole#
personnel, sorry, humanresourcescapital people read this webular travesty? My God, I hope not. ;-)He Who Shall Never Be Employed AgainBen Poole#
Lies, damned lies, and benchmarks, and all that, so I finally got around to testing it. I dimmed new NotesSessions inside two routines inside an otherwise empty loop, and timed it. I can now confidently say that this halved the execution time - but over 10,000 iterations this meant from 120k loops per second it dropped to 60k loops/sec. Which I'm sure I could live with :-)
Rock, you may have converted me on the NotesSession thing… and jonvon, I agree - there are always a zillion 'under the hood' things you worry about - the normal how-to literature doesn't always fill in these blanks, and it's great to know how things *really* work.Colin Pretorius#
I also stumbled across this Dijkstra quote on another blog recently: "It is practically impossible to teach good programming style to students that have had prior exposure to BASIC: as potential programmers they are mentally mutilated beyond hope of regeneration."
Erk, where did LS come from, again? After a few years of trying to build classes in LS, I can kinda see what the man was getting at…
As for (15), I'm lucky that right now I'm the one who'd be doing the hiring, and I'll quite confidently say that I wouldn't hire anyone who doesn't regularly visit sites like yours, notestips, lotusgeek, codestore etc. I think there are precious few Notesers in South Africa who spread their research beyond the likes of LDD/notes.net, if that much. At least not in my experience
I've heard that particular Djikstra quote before: whilst he kind of had a point (!), the man was clearly too enamoured of punchcard programmers, may he rest in peace… (I speak as someone who has a whole book on that very subject. Let's not go there).
Thanks for the kind words re this and the other sites out there. Speaking for myself, I try :-D Ben Poole#
Andrew Pollack#
:-)jonvon#
And I'm with jonvon - that is a friggin' kewl name. Sounds like a Roman senator, or gladiator ;)
That's it! Colin is a CODE GLADIATOR.
(/me pounds fist in chest and says, "Hail Ceasar!")
Hmmm, codegladiator.com would make a KEWL blog name :) You get first dibs Colin…
RockRock#
RockRock#
Thanks for the dibs, Rock, but the problem with being a gladiator is that eventually someone's going to come along and lop your head off :-) (But I'm rather amazed that nobody's nabbed that domain in any form yet, it's a cool name)
And I do mean it regarding your sites (Rock, Ben) -- I have serious respect for the effort you and others expend and expertise you share. It goes back to treating one's profession as a craft, going beyond a pay cheque, or even being 'good' (iow 'just good enough') at what you do. You help people who will always want to be better at what they do, who want to advance their 'craft' - by sharing your experiences and thoughts, and by fostering a self-selecting community of people who seek out these communities because they share the mindset.
Bluntly put, someone who doesn't approach development in that way, isn't someone I'd enjoy working with (speaking from experience, here), OR entrust our company's systems to…Colin Pretorius#