File APIs for Java Developers
Manipulate DOC, XLS, PPT, PDF and many others from your application.
http://aspose.com/file-tools
The moose likes Java in General and the fly likes magic number??? Big Moose Saloon
  Search | Java FAQ | Recent Topics | Flagged Topics | Hot Topics | Zero Replies
Register / Login
JavaRanch » Java Forums » Java » Java in General
Bookmark "magic number???" Watch "magic number???" New topic
Author

magic number???

subho saha
Ranch Hand

Joined: Jun 15, 2005
Posts: 57
What is a magic number in java?
Steve Morrow
Ranch Hand

Joined: May 22, 2003
Posts: 657

Magic Numbers
Tony Morris
Ranch Hand

Joined: Sep 24, 2003
Posts: 1608
It is vernacular for an ill-founded fear whereby many developers expose constant values to excessive scope, resulting in confusion, and providing the illusion that they are contributing positively to the robustness of their software, while actually doing the contrary.

Don't believe the hype.


Tony Morris
Java Q&A (FAQ, Trivia)
paul wheaton
Trailboss

Joined: Dec 14, 1998
Posts: 20530
    ∞

A good example of a "magic number" is something like "80" in this statement:

if ( s.length() > 80 )

Some folks would call that a magic number. They think that it should be replaced with:

private static final int terminalWidth = 80 ;

...

if ( s.length() > terminalWidth )

so that you know where the "80" comes from. The added bonus is that if you later need to change that value, you can do it in one place.

My experience is that if the same number is used a lot, it's good to put it behind an identifier. But there are lots of times I think that having "magic numbers" makes my code easier to read:



Is 4 really a magic number? Some folks would argue it is. I think "4" better than "charArrayGrowthFactor" which you can look up to see that it's "4".


permaculture Wood Burning Stoves 2.0 - 4-DVD set
Ken Blair
Ranch Hand

Joined: Jul 15, 2003
Posts: 1078
Originally posted by Tony Morris:
It is vernacular for an ill-founded fear whereby many developers expose constant values to excessive scope, resulting in confusion, and providing the illusion that they are contributing positively to the robustness of their software, while actually doing the contrary.

Don't believe the hype.


Er, what? My understanding of the term magic number is that it's simply a literal number for which the logical reasoning behind it is not immediately obvious. I was not aware there was any hype surrounding it. I was also not aware a developers choice to expose or not expose it had anything to do with whether or not it's a magic number.
Stuart Ash
Ranch Hand

Joined: Oct 07, 2005
Posts: 637
Adding to what Paul's saying, even I've had this dilemma at times. I have mostly insisted that developers in my team adhere to the convention of using constants instead of magic numbers. But like he points out, there seem to be cases where using the plain number seems more logical or natural. (Will post an example when I can think of it.)

What do others here think of this.


ASCII silly question, Get a silly ANSI.
Srinivasa Raghavan
Ranch Hand

Joined: Sep 28, 2004
Posts: 1228
(Will post an example when I can think of it.)


In the above code will '0' be treated as a magic number.

I feel the above code would be better rather than writing like

public static int INITIAL_VALUE = 0; // Declared some where ..
...
for ( int counter = INITIAL_VALUE; counter < name.length(); counter++ )


Thanks & regards, Srini
MCP, SCJP-1.4, NCFM (Financial Markets), Oracle 9i - SQL ( 1Z0-007 ), ITIL Certified
Stuart Ash
Ranch Hand

Joined: Oct 07, 2005
Posts: 637
Yes, that would be one example of an unavoidable magic number.
Hemal Pandya
Greenhorn

Joined: Nov 10, 2005
Posts: 18
Originally posted by Tony Morris:
It is vernacular for an ill-founded fear whereby many developers expose constant values to excessive scope, resulting in confusion, and providing the illusion that they are contributing positively to the robustness of their software, while actually doing the contrary.

Don't believe the hype.


Claps. That's the most quotable line I have every seen on the subject. Thank you.
Steve Morrow
Ranch Hand

Joined: May 22, 2003
Posts: 657

Er, what? My understanding of the term magic number is that it's simply a literal number for which the logical reasoning behind it is not immediately obvious. I was not aware there was any hype surrounding it. I was also not aware a developers choice to expose or not expose it had anything to do with whether or not it's a magic number.


Couldn't agree more.
subho saha
Ranch Hand

Joined: Jun 15, 2005
Posts: 57
Thanks guys ...
But some body told me magic no. in java stands for the first four bytes in dot class file. They mean "CAFE BABE" attached by the original devoloper,s of oak project.This was done as a reminder of there contribution.Anybody tampering with the first four bytes in there dot class file wont be able to execute the program.
[ November 18, 2005: Message edited by: subho saha ]
Steve Morrow
Ranch Hand

Joined: May 22, 2003
Posts: 657

Ohhhh, THAT "magic number". Yes, "somebody" told you correctly. See section 4.1 here:

http://java.sun.com/docs/books/vmspec/2nd-edition/html/ClassFile.doc.html#80959
subho saha
Ranch Hand

Joined: Jun 15, 2005
Posts: 57
//==============================================================
Ohhhh, THAT "magic number". Yes, "somebody" told you correctly. See section 4.1 here:

http://java.sun.com/docs/books/vmspec/2nd-edition/html/ClassFile.doc.html#80959
//==================================================================
Yes you got it right Steve. By the way does "CAFE BABE" mean any thing special.Any history behind it.Why the hell "CAFE BABE".Some body told me they first made it "DEAD BABE" and later changed to "CAFE BABE" but could not tell me why or it's significance.
Jim Yingst
Wanderer
Sheriff

Joined: Jan 30, 2000
Posts: 18671
I think they were just playing around. There's a limited number of words & phrases you can make with exactly 8 characters in the range A-F; I would guess they were looking for something fun and/or easy to remember. When the name "Java" was chosen for the new language, there were a lot of jokes relating to coffee in some way (since "java" is slang for coffee). I imagine "CAFE" is an example of this.


"I'm not back." - Bill Harding, Twister
Ernest Friedman-Hill
author and iconoclast
Marshal

Joined: Jul 08, 2003
Posts: 24183
    
  34

Note that this usage of the phrase "magic number", like the other one, is not Java specific. Putting a "magic number" into a binary file is a common practice; on UNIX, it's often used to identify the type of a file, equivalent to what filename extensions are used for on DOS/Windows.

The first two bytes of an *.EXE file are, if memory serves, MZ, the initials of an early Microsoft intern.


[Jess in Action][AskingGoodQuestions]
Steve Morrow
Ranch Hand

Joined: May 22, 2003
Posts: 657

Yes you got it right Steve.

Just to mention, the usage of "magic number" as the first byte or two of a file is also discussed in the link I posted first...

More information can be found here:

Magic Numbers

"0xFECEFACE". LOL!
[ November 18, 2005: Message edited by: Steve Morrow ]
Maximilian Xavier Stocker
Ranch Hand

Joined: Sep 20, 2005
Posts: 381
Originally posted by Stuart Ash:
Adding to what Paul's saying, even I've had this dilemma at times. I have mostly insisted that developers in my team adhere to the convention of using constants instead of magic numbers. But like he points out, there seem to be cases where using the plain number seems more logical or natural. (Will post an example when I can think of it.)

What do others here think of this.


Magic numbers bad.

For things like collection iterations yes absolutley using

for(int i=0;i<sizeofcollection;i++{

The zero does not really qualify to me as a magic number.

However if you are going to use some pesudo-random (they don't seem random to you when you write it but to someone else later on they sure will) constants than I say create a real constant.

I say for this for two reasons

1) Your code will be more readable
2) Your code will be more maintainable.

For example I have a class that does some writing to a paged file and sometimes I need to read and/or write special ints to the index for the file. Well I need those ints all over the place. Which is better to have writeInt(-1) or writeInt(-2) or things like writeInt(_EOF) or writeInt(_EMP)

I think the latter. Plus if for some reason I should want to change those ints I only have to change it in one place... plus it is easier for me not to screw up because at least to me it is easier to read when I should use one or the other.

A quick note about my constant naming style. I like useing _ in front of constants when they are private ones as they are in this case. Which is my final point on this. Who ever said that your constant whatever has to be public? There is no need to expose anything. In fact if you have constants to replace magic numbers that are only used inside your class (most of time) then exposing them is kind of a dumb idea anyway so on that point I agree with whoever commented about that.
Ken Blair
Ranch Hand

Joined: Jul 15, 2003
Posts: 1078
I still don't understand. Is it not a magic number when it's not defined in a constant variable? I mean is 42 in "for (int i = 0; i < 42; i++) {" not a magic number? My understanding of the term must be warped because I don't see what exposing or not exposing a magic number has to do with it being a magic number nor do I see what defining a magic number as a static variable or just writing it in has to do with it either.

Sounds like more of a debate about how magic numbers should be used, not a debate about what a magic number is.
Ernest Friedman-Hill
author and iconoclast
Marshal

Joined: Jul 08, 2003
Posts: 24183
    
  34

Originally posted by Ken Blair:
My understanding of the term must be warped because I don't see what exposing or not exposing a magic number has to do with it being a magic number nor do I see what defining a magic number as a static variable or just writing it in has to do with it either.


Let's say you've got a million lines of code. In that code, the number 12 appears 143 times. Some of them represent the number of eggs in a dozen. Some of them represent the number of people on a jury. And the balance are the number of ounces of rice per package.

Starting next week, rice comes in 13.5 ounce packages. Fix the code.

Not so easy, is it? Don'tcha wish you'd used DOZEN, JURY_SIZE, and OZ_PER_PKG instead? Now instead of changing the definition of OZ_PER_PKG in one place, you have to look at 143 different places in the code, and figure out which ones to change. Not fun.

12 is a magic number. OZ_PER_PKG is a named constant. Named constants are better.
Stefan Wagner
Ranch Hand

Joined: Jun 02, 2003
Posts: 1923

... and we didn't speak of the 2 family-packs in the code, which are packs of 5 packages of rice.
They might be 60 ounce per package instead of 5 * 12, and aren't catched with a 'replace all, confirm change'.


http://home.arcor.de/hirnstrom/bewerbung
Ilja Preuss
author
Sheriff

Joined: Jul 11, 2001
Posts: 14112
Originally posted by Ernest Friedman-Hill:
12 is a magic number. OZ_PER_PKG is a named constant. Named constants are better.


Of course the constant declaration still contains the number 12, but there is nothing "magic" about it because the constant name should reveal its meaning.

A "magic number", again, is a number literal which's meaning isn't totally obvious.


The soul is dyed the color of its thoughts. Think only on those things that are in line with your principles and can bear the light of day. The content of your character is your choice. Day by day, what you do is who you become. Your integrity is your destiny - it is the light that guides your way. - Heraclitus
Ilja Preuss
author
Sheriff

Joined: Jul 11, 2001
Posts: 14112
Originally posted by Srinivasa Raghavan:

In the above code will '0' be treated as a magic number.


I wouldn't call it a magic number, simply because the idiom is so well known that every java developer should understand the meaning without even having to think about it.

If the loop wouldn't start at zero but, say, at four, that would be a magic number to me.
Ilja Preuss
author
Sheriff

Joined: Jul 11, 2001
Posts: 14112
Originally posted by Tony Morris:
It is vernacular for an ill-founded fear whereby many developers expose constant values to excessive scope, resulting in confusion, and providing the illusion that they are contributing positively to the robustness of their software, while actually doing the contrary.


Give me an example of a constant that results in confusion, and I bet I can show you a solution without a magic number that is better than the equivalent with the magic number.

The certainly can do damage by misapplying the technique of extracting a constant - most often by giving it a bad name and/or scope. That doesn't mean that the technique itself isn't valuable.
Ilja Preuss
author
Sheriff

Joined: Jul 11, 2001
Posts: 14112
Originally posted by Paul Wheaton:


Is 4 really a magic number? Some folks would argue it is.


Me, for example.

I think "4" better than "charArrayGrowthFactor" which you can look up to see that it's "4".


Why do you think that?

When I read the code, I will typically be more interested in why it is multiplying the length by 4, and less concerned about the value itself. The name helps me understand that it's simply the array growing by some arbitrary factor without having to interprete the surrounding code.

It could even be named "arbitraryGrowthFactor" or "growthFactorOptimizedForSpeed" or something.
Tony Morris
Ranch Hand

Joined: Sep 24, 2003
Posts: 1608
Originally posted by Ilja Preuss:


Give me an example of a constant that results in confusion, and I bet I can show you a solution without a magic number that is better than the equivalent with the magic number.

The certainly can do damage by misapplying the technique of extracting a constant - most often by giving it a bad name and/or scope. That doesn't mean that the technique itself isn't valuable.


I'll bet you can show me an example where you shift the "magic number" (cough choke) to a different position, that exceeds required scope (implies requirement defect). You cannot "omit" the "magic number", unless you redefine the term, which is yet to have any real definition stated (hence its superficial existance).
Jim Yingst
Wanderer
Sheriff

Joined: Jan 30, 2000
Posts: 18671
Well, glad we cleared that up. Silly me, I'd been thinking it was trivially easy to choose appropriate access modifiers and scope for constants to avoid exposing them unnecessarily. Generally I'd use a final local for a number used in only one method; a private static final for a number used in multiple methods in the same class, and some other access modifier if there was any legitimate reason to expose them more widely. (Bearing that this could create problems if this value ever changes without recompiling client fiels.) But I guess I'm just a victim of all that danged hype we keep seeing. Oh well...
Tony Morris
Ranch Hand

Joined: Sep 24, 2003
Posts: 1608
Is this the bit where I highlight that we are such an arrogant species, and that advertising it with sarcasm makes me cringe in the name of humanity, followed by the deletion of the post, and one of those clever little private messages informing me that I must align my line of reasoning with The Authority or burn?

Let's just get straight to it.
Jim Yingst
Wanderer
Sheriff

Joined: Jan 30, 2000
Posts: 18671
Nope. After my past private messages were apparently not understood in the manner intended, I decided it would be better to simply let your messages stand intact, that everyone could evaluate them for themselves, for better or worse. My few past attempts to moderate you were based on your tone, not your content. It appears you either did not understand that or did not believe that. OK, whatever. I haven't touched any of your posts since the last PM (almost two months ago), and I won't. Your ideas can live or die based on your ability to express them in a clear fashion. Or not.

In this case I disagreed with you, and commented on it. Probably more snidely than is appropriate for JavaRanch. I'll try to avoid that. Though based on your past behavior I have a hard time mustering much sympathy for you on this issue - I'm just concerned with setting a bad precendent for others.

So - do you have any response to the on-topic issues here? I.e. related to Java programming? I'm saying that I think scope and access modifiers can be decided independently of the decision to replace a "magic number" with a constant variable. If I use a local constant variable to minimize or explain use of a numeric literal in a method, does that cause some problem? Or if I use a private static constant, same question? Or are you saying that worrying about "magic numbers" make people predisposed to make public constants? The last, I might agree with, but your initial statements in this thread seem to imply that avoiding "magic numbers" is inherently wrong. I think it's a good idea which can be misapplied, e.g. by creating public constants when private would do. If you disagree, can you elaborate?
Ilja Preuss
author
Sheriff

Joined: Jul 11, 2001
Posts: 14112
Originally posted by Tony Morris:
I'll bet you can show me an example where you shift the "magic number" (cough choke) to a different position, that exceeds required scope (implies requirement defect). You cannot "omit" the "magic number", unless you redefine the term, which is yet to have any real definition stated (hence its superficial existance).


Idle talk. Show us some code that we can discuss and transform. Keep in mind that I stated above which definition I use. If it isn't yet clear to you, ask for clarification. If you use a different one, explain.

And you keep coming up with this term "requirement defect" without defining it. If someone understands what it means and how it is connected to the current topic, please signal.

----
"If what you have to say is no better than silence, keep silent." - Caine
Tony Morris
Ranch Hand

Joined: Sep 24, 2003
Posts: 1608
I'm always the one who has to provide proof. I call unfair. Just because it's not in all the text books... OK, I'll stop whinging now.

A definition has not been provided, only some loose talk. Therefore, I'll provide a context. Feel free to clarify it. If it suits your definition, I'll point out why it exceeds scope. I think it should be obvious though.

Maximilian Xavier Stocker
Ranch Hand

Joined: Sep 20, 2005
Posts: 381
Originally posted by Tony Morris:
I'm always the one who has to provide proof. I call unfair. Just because it's not in all the text books... OK, I'll stop whinging now.

A definition has not been provided, only some loose talk. Therefore, I'll provide a context. Feel free to clarify it. If it suits your definition, I'll point out why it exceeds scope. I think it should be obvious though.



Is the typo on purpose? Normally I would say no but maybe that's something you are trying to demonstrate. And could you please explain what you are trying to demonstrate with this example and what is right or wrong about it because I don't find it very clear. The example is concise yes but I don't understand what point you are trying to demonstrate with this.
Ilja Preuss
author
Sheriff

Joined: Jul 11, 2001
Posts: 14112
Originally posted by Tony Morris:
I'm always the one who has to provide proof. I call unfair.


I'm sorry for the misunderstanding - I didn't want proof. All I wanted was something more concrete, because I simply found your previous statement to be too unspecific to work with it - it didn't mean anything to me. And I apologize for the rough tone.

A definition has not been provided, only some loose talk.


To me, a magic number (in the context we discuss here) is a number literal whichs meaning isn't immediately obvious to the reader. Don't know wether that makes for an adequate definition to you, but it works reasonably well for me to decide wether to introduce some kind of "symbolic identifier" for it.



Well, I think

System.out.println("Snow White and the 7 Dwarfs");

would probably be just fine. The "7" really isn't that "magic" in this case...

But to go with your example, what do you think about


void m()
{
final int numberOfDwarfs = 7;
System.out.println("Snow White and the " + numberOfDwarfs + " Dwarfs");
}


as Jim already suggested?

As an aside, if declaring the constant with class scope instead of method scope causes you bigger trouble, I would be concerned about the size of your classes...
Ken Blair
Ranch Hand

Joined: Jul 15, 2003
Posts: 1078
Originally posted by Paul Wheaton:
A good example of a "magic number" is something like "80" in this statement:

if ( s.length() > 80 )

Some folks would call that a magic number. They think that it should be replaced with:

private static final int terminalWidth = 80 ;

...

if ( s.length() > terminalWidth )

so that you know where the "80" comes from. The added bonus is that if you later need to change that value, you can do it in one place.

My experience is that if the same number is used a lot, it's good to put it behind an identifier. But there are lots of times I think that having "magic numbers" makes my code easier to read:



Is 4 really a magic number? Some folks would argue it is. I think "4" better than "charArrayGrowthFactor" which you can look up to see that it's "4".


Is the premise that this is the only place it's used, or is the "growth factor" being used in other places within the class? If it's just there, I agree with you but I think it should be documented there as well. If it's other places, then it might be more appropriate to have it named.

Originally posted by Ernest Friedman-Hill:


Let's say you've got a million lines of code. In that code, the number 12 appears 143 times. Some of them represent the number of eggs in a dozen. Some of them represent the number of people on a jury. And the balance are the number of ounces of rice per package.

Starting next week, rice comes in 13.5 ounce packages. Fix the code.

Not so easy, is it? Don'tcha wish you'd used DOZEN, JURY_SIZE, and OZ_PER_PKG instead? Now instead of changing the definition of OZ_PER_PKG in one place, you have to look at 143 different places in the code, and figure out which ones to change. Not fun.

12 is a magic number. OZ_PER_PKG is a named constant. Named constants are better.


Terminology is one of my chief weaknesses. I didn't realize "magic number" implied that the number was not a named constant and was just written into the code. I'd definitely agree that in many situations a magic number is not appropriate, although when it's not reused simply documenting it would probably be better than making a variable.

Originally posted by Tony Morris:
I'm always the one who has to provide proof. I call unfair. Just because it's not in all the text books... OK, I'll stop whinging now.

A definition has not been provided, only some loose talk. Therefore, I'll provide a context. Feel free to clarify it. If it suits your definition, I'll point out why it exceeds scope. I think it should be obvious though.



Forgive me, but I don't see how an example of abusing the technique invalidates the technique. Is this not valid:



I know the idea of hardcoding some arbitrary limit into a class like that would probably make your skin crawl, it does mine. However, if you assume as a premise that this class has a maximum number of records and it's appropriate to be hardcoded, is the technique wrong?
Tony Morris
Ranch Hand

Joined: Sep 24, 2003
Posts: 1608
Originally posted by Ken Blair:


Is 4 really a magic number? Some folks would argue it is. I think "4" better than "charArrayGrowthFactor" which you can look up to see that it's "4".<hr></blockquote>

Is the premise that this is the only place it's used, or is the "growth factor" being used in other places within the class? If it's just there, I agree with you but I think it should be documented there as well. If it's other places, then it might be more appropriate to have it named.

[/qb]<hr></blockquote>

Forgive me, but I don't see how an example of abusing the technique invalidates the technique. Is this not valid:



I know the idea of hardcoding some arbitrary limit into a class like that would probably make your skin crawl, it does mine. However, if you assume as a premise that this class has a maximum number of records and it's appropriate to be hardcoded, is the technique wrong?[/QB]


There was a typo in my original example. I didn't "abuse the technique"; I merely asked for a definition, for which that definition does not meet *your* world view (and that there are zillions of other world views suggests an underlying flaw, don't you think?). Let's use *your* definition anyway, since any other is an "abuse", right? Of course.

You have exposed a field to excessive scope, assuming that field is not used in all methods and nested classes of that class. However, if all methods do indeed use that "magic number", then they each have their own implementation details which are not dependant on each other and so should define themselves to their local context, since if they are, then they are in violation of "perfect symbiosis of contractual operations". If you have followed the somewhat simplistic reasoning up to here, and you really care to know what I mean about by last statement, you'll have to wait. Otherwise, if it is irrelevant (that you do acknowledge that excessive scope has occurred), then ignore it (since I'm starting to get over it pretty quickly) and move on.

Let's use some other example (if I can paraphrase it right):


Again, excessive scope. Why does the entire method need to know about x? Why not just the call to blah(int)? What if I wrote some more code after that method call; why should I be exposed to such a thing as 'x'?

Let's look at a related text book example:

All the text books say to use the latter, and not the former (you've read that one haven't you?). The reasoning for this is excessive scope. That is, 'i' is exposed to a scope that exceeds what is required. I won't go into who excessive scope is implicitly a requirement defect, for brevity, and to prevent pain.

An interesting observation is that I can explain these extremely simple concepts to my undergraduate students who will immediately follow up with meaningful questions and curiosity, yet the claimed "experienced" people (who read all of those books that talk about such things as the feared magic numbers) fail to "get it".

That there is propaganda/marketing guff/bollocks/<preferred-term> at work is merely speculation, but it's my most plausible explanation so far. Of course, I could be totally wrong, and I'm missing some major point, but all the dribble so far is straight from the aforementioned text books, so I'm forced to believe otherwise. Trust me, I love learning; this is not a penis extending exercise.
Stan James
(instanceof Sidekick)
Ranch Hand

Joined: Jan 29, 2003
Posts: 8791
With all the indenting, bolding and horizontal lining I lost track of which things in that post you support and which you don't. I rather liked this example of extracting a magic number to a final variable (with the brace alignment fixed )

It runs the risk of exposing the "constant" to methods that don't need it. Perhaps that tells us the methods don't belong in the same class together. Perhaps it's a compromise we're willing to recognize and live with. Few things are perfect. I don't call out "Broken leading tone!" every time I hear a blues tune go from the V chord to the IV chord. I've even taught the gullible young school children to play the blues. I can tolerate the risks that go with having "6" visible to other methods.


A good question is never answered. It is not a bolt to be tightened into place but a seed to be planted and to bear more seed toward the hope of greening the landscape of the idea. John Ciardi
Ilja Preuss
author
Sheriff

Joined: Jul 11, 2001
Posts: 14112
Originally posted by Ken Blair:
I'd definitely agree that in many situations a magic number is not appropriate, although when it's not reused simply documenting it would probably be better than making a variable.


Better in which ways?
Ilja Preuss
author
Sheriff

Joined: Jul 11, 2001
Posts: 14112
Originally posted by Tony Morris:
that there are zillions of other world views suggests an underlying flaw, don't you think?


I don't think so.

For example, there is no agreed upon definition of what makes a method "long". For some people "long" means more than fits on the screen, for others more than five lines of code. And it even might depend on the specific method, or I might answer differently when you ask me tomorrow. Still that doesn't mean that the concept of "methods being too long" is worthless, that we can't productively discuss it, come to interesting conclusions and learn from each other.

I know it's hard for software engineers, but some things simply are fuzzy and need individual evaluation - not because they are flawed, but because that is how they work best, because hard and fast rules wouldn't work.

if all methods do indeed use that "magic number", then they each have their own implementation details which are not dependant on each other and so should define themselves to their local context, since if they are, then they are in violation of "perfect symbiosis of contractual operations". If you have followed the somewhat simplistic reasoning up to here, and you really care to know what I mean about by last statement, you'll have to wait.


I understand neither what "define themselves to their local context" means, nor what a "perfect symbiosis of contractual operations" is, so I am anxious to read your elaboration. I'd just like to notice that in my opinion software development seldom (though not never) is about perfectionism regarding one force, but more often about balancing competing forces.




Again, excessive scope. Why does the entire method need to know about x?


Well, if x would tell me something that 7 doesn't, because it's more expressive, of course. What is the harm done, in this specific case?

What if I wrote some more code after that method call; why should I be exposed to such a thing as 'x'?


If it bothers you, don't do it - keep the scope of x clean by introducing a surrounding block, or by extracting another method.

I won't go into who excessive scope is implicitly a requirement defect, for brevity, and to prevent pain.


I haven't yet seen an example where giving a magic number a name *forces* you to introduce excessive scope, only examples where you *choose* to not use a solution that would have prevented the scope.

That isn't to say that I'm bothered as much about the scope as you seem to be - the for-loop example is trivial because there is no competing force. When there is one, we have to balance them. Blindly having one force always win doens't sound like a very sensible way of working to me, but I might still not fully understanding what you are getting at.

What is your alternative *in Java*? Would you really prefer a comment?

An interesting observation is that I can explain these extremely simple concepts to my undergraduate students who will immediately follow up with meaningful questions and curiosity, yet the claimed "experienced" people (who read all of those books that talk about such things as the feared magic numbers) fail to "get it".


Yes, that is interesting.

That there is propaganda/marketing guff/bollocks/<preferred-term> at work is merely speculation, but it's my most plausible explanation so far.


I *think* I have another one.

Most students didn't yet experience some of the forces that the more "experienced" people are confronted with, naturally. (And unfortunately, that seems to be also true for a lot of text book authors.) So they don't feel the need to balance those forces - they can concentrate on a subset of the forces (what some people would call "academic") and have the luxury of being ignorant of the other. It's no wonder to me that they find a quite different balance.
Ken Blair
Ranch Hand

Joined: Jul 15, 2003
Posts: 1078
Originally posted by Ilja Preuss:
Better in which ways?


The variable isn't created unnecessarily and kept in scope unnecessarily just to use it in one single line of code and never again. Note the premise is a "magic number" being used in one line and only one line.

Originally posted by Tony Morris:
There was a typo in my original example. I didn't "abuse the technique"; I merely asked for a definition, for which that definition does not meet *your* world view (and that there are zillions of other world views suggests an underlying flaw, don't you think?). Let's use *your* definition anyway, since any other is an "abuse", right? Of course.


I wasn't suggesting that any part of your example was invalid or abusive because of a typo. I thought you were arguing it was excessive scope and thus shouldn't be used. My point was that yes, it is excessive scope, but is only a reason it shouldn't be used in that case and doesn't invalidate every use of it in other cases.

Originally posted by Tony Morris:
You have exposed a field to excessive scope, assuming that field is not used in all methods and nested classes of that class. However, if all methods do indeed use that "magic number", then they each have their own implementation details which are not dependant on each other and so should define themselves to their local context, since if they are, then they are in violation of "perfect symbiosis of contractual operations". If you have followed the somewhat simplistic reasoning up to here, and you really care to know what I mean about by last statement, you'll have to wait. Otherwise, if it is irrelevant (that you do acknowledge that excessive scope has occurred), then ignore it (since I'm starting to get over it pretty quickly) and move on.


In the example whether or not it was exposed to excessive scope depends on what other methods and/or nested classes are in. If all other methods used that constant and there were no nested classes, or the nested classes and their methods all used that constant then I don't think it's exposed to excessive scope. In those cases is it not valid?

I'll acknowledge that in most cases chances are it would be excessive scope. In those cases, on a purely intellectual level I agree with you that it's not a good practice. When coding in the "real world" with Java there are some cases where I'm willing to live with benign excessive scope for the sake of simplicity and readability. However, I just realised that I cannot actually think of a single example where I've ever done that nor can I think of an example where I would do that. I'm not quite ready to dismiss the idea entirely though.

Originally posted by Tony Morris:
Let's use some other example (if I can paraphrase it right):


Again, excessive scope. Why does the entire method need to know about x? Why not just the call to blah(int)? What if I wrote some more code after that method call; why should I be exposed to such a thing as 'x'?

Let's look at a related text book example:


Those are good examples of when I think it would be very foolish to declare it. I never suggested you should do it in those cases and have said exactly the opposite. Perhaps you're replying to someone else though.

Originally posted by Tony Morris:
All the text books say to use the latter, and not the former (you've read that one haven't you?). The reasoning for this is excessive scope. That is, 'i' is exposed to a scope that exceeds what is required. I won't go into who excessive scope is implicitly a requirement defect, for brevity, and to prevent pain.


I didn't need a text book to explain to me why that's bad, it's simple logic. But I never suggested anyone do anything like that so this must be aimed at someone else.

Originally posted by Tony Morris:
An interesting observation is that I can explain these extremely simple concepts to my undergraduate students who will immediately follow up with meaningful questions and curiosity, yet the claimed "experienced" people (who read all of those books that talk about such things as the feared magic numbers) fail to "get it".


Never read a single text book about magic numbers or being afraid of them. I was taught to declare a magic number only when it is appropriate to do so and document it the rest of the time (and it's usually the case). To reiterate, my definition of "appropriate" would be when it's reused within a given scope. Though I occassionally break that definition when it's just a couple lines in the same place reusing it.

Originally posted by Tony Morris:
That there is propaganda/marketing guff/bollocks/<preferred-term> at work is merely speculation, but it's my most plausible explanation so far. Of course, I could be totally wrong, and I'm missing some major point, but all the dribble so far is straight from the aforementioned text books, so I'm forced to believe otherwise. Trust me, I love learning; this is not a penis extending exercise.


I haven't seen any of the books and what not that are saying magic numbers are evil and to declare them in any of the examples I've seen you provide.
Jim Yingst
Wanderer
Sheriff

Joined: Jan 30, 2000
Posts: 18671
Most comments I might make have been made by Ilja and/or Ken recently. In fact yesterday I had the odd experience of composing a longish reply and posting it, only to find that Ilja had made exactly the same set of points 20 minutes earlier (see November 20, 2005 11:04 AM). So I simply deleted mine as in retrospect it had nothing to add.

This time I do see one area I'd like to comment on:

[B][Tony]: Let's look at a related text book example:

All the text books say to use the latter, and not the former (you've read that one haven't you?). The reasoning for this is excessive scope. That is, 'i' is exposed to a scope that exceeds what is required. I won't go into who excessive scope is implicitly a requirement defect, for brevity, and to prevent pain.[/B]

In the case of the for loops, excess scope is a more notable problem because many of us reuse very simple variable names in our loops, such as i for an integer, or it or iter for an Iterator. Using a for loop to limit the scope significantly reduces (but does not eliminate) the possibility of an accidental name collision which might result in a bug. In contrast when we introduce a named constant to eliminate a magic number, most of us make a point of creating a nice descriptive identifier long enough to make clear the purpose of the number. In so doing we also vastly reduce the chance that someone will accidentally use the same name to refer to something which should be different. I.e. if you've got a constant named NUM_DWARFS and someone decides to use that name multiple times, it's probably because they really and truly do intend to be referring to the exact same value. (Be it 7 or 13 or whatever.) The chance of a mixup here is much much less than is was for variables like "i" or "it". Yeah, there's still some risk I suppose, e.g. if one programmer is talking about Snow White while another is referring to The Hobbit. Still, I think the risk is fairly small, and it should be balanced against the benefits already discussed by others, usually making the code more readable and more maintainable.

Personally I've observed numerous bugs in the field which were caused by magic numbers - especially when it's a reused number and someone changes it, but fails to change all occurrences of the number. In contrast, I can't recall ever observing problems related to excess scope of a named constant. (While I certainly can recall problems with excess scope of an "i" or "it".) So, for myself I have no problem recommending replacing magic numbers with named constants in most cases. Especially in cases where the number is reused at least once. If your experience is significantly different in this regard, I'd like to hear more examples.
[ November 21, 2005: Message edited by: Jim Yingst ]
Ernest Friedman-Hill
author and iconoclast
Marshal

Joined: Jul 08, 2003
Posts: 24183
    
  34

Originally posted by Jim Yingst:
In contrast, I can't recall ever observing problems related to excess scope of a named constant.


Indeed, and this is my little challenge-the-orthodoxy soapbox. I've had the "constant interface antipattern" explained to me many times, and I've worked on code that used it, and code that didn't. And I've never seen it lead to any problems. My feeling is that in Java, anyway, if you use any sort of real IDE, you have no problems knowing exactly where everything is defined. The supposed problems caused by this "antipattern" are grossly exaggerated.

So... what is a "requirements defect," anyway? Joel Spolsky says

a requirements defect is when the requirements are wrong; the cure is to change the requirements.

And indeed, that's how several other sources use the phrase. There are actually only 427 hits for "requirements defect" (with the quotes) on Google.

I don't understand how defining a constant with excessive scope (an implementation detail) is related in any way to requirements, let alone how it represents a requirements defect. Can somebody fill me in?
 
 
subject: magic number???