Placement of Constants

R

Rhino

I'm really hoping this will be a straightforward non-controversial question
(for a change) on my part ;-)

I am doing a code review on some code that I want to put in a "code
portfolio" so I'm trying to figure out the best ways to do various things.

Specifically, I have about 20 classes right now in the main part of the
project that I'll be putting in the portfolio. There are a substantial
number of constants used in one place or another. I have _most_ of them in
a single class that is called FooConstants (where "Foo" is replaced by the
name of my project.) FooConstants has a private constructor that throws
UnsupportedOperationException (as suggested previously in this group) and
everything else in it is a static final, i.e. a constant.

Is there any reason NOT to put _all_ of the constants used throughout the
project in FooConstants? Or is it wiser to only move something to a
XXXConstants class if it is used in more than one class?

For instance, if I have a constant named FOO_FILE_NAME and it is used only
in class FooBlahBlah, is it better to leave the constant in FooBlahBlah
rather than forcing developers to have to go to another class to determine
(or change) its value? Or is it better to have all constants, wherever
used, all together in FooConstants?

Am I safe in assuming that if a Constant is used in more than one class and
it is supposed to have the same value in each case, that I definitely want
those constants centralized in my FooConstants class? Otherwise, if I put a
unique occurrence of each multiply-occuring constant, like FOO_LOG_PATH, in
each class where it occurs, it seems to be almost inevitable that
FOO_LOG_PATH will eventually have different values in each of the classes
where it is used.
 
M

markspace

Rhino said:
Is there any reason NOT to put _all_ of the constants used throughout the
project in FooConstants? Or is it wiser to only move something to a
XXXConstants class if it is used in more than one class?


I would do the opposite: move constants out of FooConstants and into
classes that are closer to where they belong conceptually or are consumed.

For example, JFrame.EXIT_ON_CLOSE (from memory, didn't compile check
that) gets used a lot in many of my applications, and indeed all over
the place in Swing applications in general. Does Sun put EXIT_ON_CLOSE
in a separate SunConstants class? Nope, the keep EXIT_ON_CLOSE close to
where it belongs and where it is used (consumed).

This makes more sense as applications grow larger. Can you imagine what
the size of SunConstants would be if Sun actually put every constant in
their API in that class? Yuck. It would be a nightmare to document or
read. So it's probably better that the constants relating to the JFrame
API are in the JFrame class, where you'd expect to find them, and expect
to see them documented.

Just my 2 cents here.
 
A

Arne Vajhøj

I'm really hoping this will be a straightforward non-controversial question
(for a change) on my part ;-)

I am doing a code review on some code that I want to put in a "code
portfolio" so I'm trying to figure out the best ways to do various things.

Specifically, I have about 20 classes right now in the main part of the
project that I'll be putting in the portfolio. There are a substantial
number of constants used in one place or another. I have _most_ of them in
a single class that is called FooConstants (where "Foo" is replaced by the
name of my project.) FooConstants has a private constructor that throws
UnsupportedOperationException (as suggested previously in this group) and
everything else in it is a static final, i.e. a constant.

Is there any reason NOT to put _all_ of the constants used throughout the
project in FooConstants? Or is it wiser to only move something to a
XXXConstants class if it is used in more than one class?

For instance, if I have a constant named FOO_FILE_NAME and it is used only
in class FooBlahBlah, is it better to leave the constant in FooBlahBlah
rather than forcing developers to have to go to another class to determine
(or change) its value? Or is it better to have all constants, wherever
used, all together in FooConstants?

Am I safe in assuming that if a Constant is used in more than one class and
it is supposed to have the same value in each case, that I definitely want
those constants centralized in my FooConstants class? Otherwise, if I put a
unique occurrence of each multiply-occuring constant, like FOO_LOG_PATH, in
each class where it occurs, it seems to be almost inevitable that
FOO_LOG_PATH will eventually have different values in each of the classes
where it is used.

XxxxConstants with constants is not a very good pattern.

I would definitely move the constants to the classes where they
logical belong.

Typical the class that has methods that expects those
constants as input.

Also use enum instead of int constants for additional
type safety when possible.

For configuration stuff then use a configuration file
for flexibility. If it is a simple case then good old
Properties class should be sufficient.

Filenames and directories belong to the last category.

Arne
 
L

Lew

Rhino said:
Specifically, I have about 20 classes right now in the main part of the
project that I'll be putting in the portfolio. There are a substantial
number of constants used in one place or another. I have _most_ of them in
a single class that is called FooConstants (where "Foo" is replaced by the
name of my project.) FooConstants has a private constructor that throws
UnsupportedOperationException (as suggested previously in this group) and
everything else in it is a static final, i.e. a constant.

It's silly to throw that exception in the private constructor. Only the class
itself can invoke the constructor. I prefer a private constructor with an
empty body.

"static final" is not the same as a "constant variable" in Java. A constant
can be non-static, and a final can be non-constant.
Is there any reason NOT to put _all_ of the constants used throughout the
project in FooConstants? Or is it wiser to only move something to a
XXXConstants class if it is used in more than one class?

Depends. Probably not wise to put them all in one place - some constants (or
static finals) should be private, not public, ergo kept in the class where
they're used. Tightly coupling classes together is a bad idea often.

Like everything else, you have to do what makes sense. Some constants should
be in a project-wide class, sure. Others in a functional unit, for example,
data-access constants in a data-access utility class. Others should be
package-private. Some should be protected or private, for use only in an
inheritance hierarchy or the class itself, respectively.

You have to think each choice through. Access should be as wide as needed but
not wider, and as narrow as possible but not narrower.
For instance, if I have a constant named FOO_FILE_NAME and it is used only
in class FooBlahBlah, is it better to leave the constant in FooBlahBlah
rather than forcing developers to have to go to another class to determine
(or change) its value? Or is it better to have all constants, wherever
used, all together in FooConstants?

I usually put static finals generally, and constants particularly, as private
in the class where they're needed, and give them wider access only when needed
as needed. YAGNI.
Otherwise, if I put a
unique occurrence of each multiply-occuring constant, like FOO_LOG_PATH, in
each class where it occurs, it seems to be almost inevitable that
FOO_LOG_PATH will eventually have different values in each of the classes
where it is used.

Logging is usually configured in an external resource, like the
log4j.properties file for the log4j framework.
 
R

Rhino

I would do the opposite: move constants out of FooConstants and into
classes that are closer to where they belong conceptually or are
consumed.

For example, JFrame.EXIT_ON_CLOSE (from memory, didn't compile check
that) gets used a lot in many of my applications, and indeed all over
the place in Swing applications in general. Does Sun put
EXIT_ON_CLOSE in a separate SunConstants class? Nope, the keep
EXIT_ON_CLOSE close to where it belongs and where it is used
(consumed).

This makes more sense as applications grow larger. Can you imagine
what the size of SunConstants would be if Sun actually put every
constant in their API in that class? Yuck. It would be a nightmare
to document or read. So it's probably better that the constants
relating to the JFrame API are in the JFrame class, where you'd expect
to find them, and expect to see them documented.

Just my 2 cents here.

I hadn't thought of the issue the way you present it. You make a lot of
good points. Thanks Markspace!
 
R

Rhino

XxxxConstants with constants is not a very good pattern.

I would definitely move the constants to the classes where they
logical belong.

Typical the class that has methods that expects those
constants as input.

Also use enum instead of int constants for additional
type safety when possible.
Yes, I do that when practical.
For configuration stuff then use a configuration file
for flexibility. If it is a simple case then good old
Properties class should be sufficient.

Filenames and directories belong to the last category.
And there is the answer to my big concern: constants that are used in
several places. I expect that as I analyze them, a lot will turn out to
be filenames and directories. or configuration information which would be
better placed in properties files....

Thanks Arne!
 
R

Rhino

Lew said:
It's silly to throw that exception in the private constructor. Only
the class itself can invoke the constructor. I prefer a private
constructor with an empty body.
Someone on this group recommended that approach to me a few years back. I
don't remember who and I probably wouldn't say if I did; everyone's
entitled to be wrong once in a while ;-)

I always wondered why that exception was supposed to be useful....
"static final" is not the same as a "constant variable" in Java. A
constant can be non-static, and a final can be non-constant.
Sorry, once again I'm being imprecise. Blame it on the fact that my
knowledge of the terminology is less than complete....

The reason this question is coming up is probably that I slavishly
followed advice I was given at some point in the past and never really
understood all the reasons for that advice - or why it might not be the
right advice.

Originally, I seem to recall putting constants in interfaces, then being
told it was bad - I forget why - and that a standalone class for
constants alone (the ones that public static final and where you write
the names in caps with underscores for separators) was the way to go (as
well as the private constructor).

Obviously, I have to rethink this now too.

Man, it seems like I'm having to rethink just about everything I've
written. Working alone without a live mentor or regular walkthroughs with
people who know more than you can definitely put you into a bad place....

Maybe I need a different job strategy: instead of trying to convince
employers/clients that I know what I'm doing, appeal to them for a job on
the grounds that I want to learn how to do things RIGHT, instead of
floundering like this.....
Depends. Probably not wise to put them all in one place - some
constants (or static finals) should be private, not public, ergo kept
in the class where they're used. Tightly coupling classes together is
a bad idea often.
Okay....

Like everything else, you have to do what makes sense. Some constants
should be in a project-wide class, sure. Others in a functional unit,
for example, data-access constants in a data-access utility class.
Others should be package-private. Some should be protected or
private, for use only in an inheritance hierarchy or the class itself,
respectively.

You have to think each choice through. Access should be as wide as
needed but not wider, and as narrow as possible but not narrower.
Okay....

Darn, I was hoping that at least one thing in Java would be a simple
obvious thing that I wouldn't have to think about for a long time.

I LOVE what this language can do but it's discouraging to find that every
tiny thing needs to be thought of very carefully to keep from doing
something that will have bad consequences. COBOL, REXX and CSP were
definitely easier in that regard ;-) But so much more limited too!
I usually put static finals generally, and constants particularly, as
private in the class where they're needed, and give them wider access
only when needed as needed. YAGNI.
That's the second time I've seen YAGNI in the last few days but I still
don't know what it means. I'm guessing it's something like YMMV, Your
Mileage May Vary?
Logging is usually configured in an external resource, like the
log4j.properties file for the log4j framework.
Right. Like Arne said, things like that should be in a properties file,
coded as constants. Now I just have to get clearer on what should and
shouldn't be put in properties files. I may not have a lot of constants
in a centralized class by the time I'm done this exercise :)

Thanks for your guidance, Lew!
 
L

Lew

Rhino said:
obvious thing that I wouldn't have to think about for a long time.

I LOVE what this language can do but it's discouraging to find that every
tiny thing needs to be thought of very carefully to keep from doing
something that will have bad consequences. COBOL, REXX and CSP were
definitely easier in that regard ;-) But so much more limited too!

Java is no different from other languages in this regard. The kind of
"think[ing] about for a long time" to which you refer is universal to
programming, not specific to Java.
That's the second time I've seen YAGNI in the last few days but I still
don't know what it means. I'm guessing it's something like YMMV, Your
Mileage May Vary?

The acronym was explained to you when you asked before. By more than one.
Why did you ignore the answers?

I only used the acronym because I "knew" you knew what it meant by now.

There's really no point in answering questions for someone who ignores the
answers.

Now go google it, for Chrissake!

Sheesh.
 
A

Arne Vajhøj

Man, it seems like I'm having to rethink just about everything I've
written. Working alone without a live mentor or regular walkthroughs with
people who know more than you can definitely put you into a bad place....

Maybe I need a different job strategy: instead of trying to convince
employers/clients that I know what I'm doing, appeal to them for a job on
the grounds that I want to learn how to do things RIGHT, instead of
floundering like this.....

Or just conclude that something is good enough.

If your ambition is to write 10000 lines of perfect code, then
you will not be done until year 2050 (or maybe 2150).

There is always something that can be improved.

In 2 years you will write much better code than what you do now. But
in 4 years you will write much better code than what you will in 2
years. And so on.

Arne
 
J

Joshua Cranmer

I always wondered why that exception was supposed to be useful....

Well, since you yourself seemed surprised at the utility, you should
probably have inquired as to why this should be done. A good tip for the
future. At worst, you learn something; at best, you avoid bad advice.
Originally, I seem to recall putting constants in interfaces, then being
told it was bad - I forget why - and that a standalone class for
constants alone (the ones that public static final and where you write
the names in caps with underscores for separators) was the way to go (as
well as the private constructor).

Putting constants in standalone classes is right for some cases.
Nowadays, I believe most of those cases have been subsumed by the
introduction of enums.
Darn, I was hoping that at least one thing in Java would be a simple
obvious thing that I wouldn't have to think about for a long time.

All rules have exceptions. A key part of design, in my opinion, is being
able to coherently explain why the particular design and implementation
was chosen. Design is a necessarily thought-intensive process, so don't
worry about having to think about it. I can show you many train wrecks
I've written that have come about by insufficient design (granted, a
project due in a week that I'll likely never refer to again isn't
something I'm too worried about turning into a train wreck).
 
A

Arved Sandstrom

Rhino wrote:
[ SNIP ]
The reason this question is coming up is probably that I slavishly
followed advice I was given at some point in the past and never really
understood all the reasons for that advice - or why it might not be the
right advice.

Originally, I seem to recall putting constants in interfaces, then being
told it was bad - I forget why - and that a standalone class for
constants alone (the ones that public static final and where you write
the names in caps with underscores for separators) was the way to go (as
well as the private constructor).

Obviously, I have to rethink this now too.

Man, it seems like I'm having to rethink just about everything I've
written. Working alone without a live mentor or regular walkthroughs with
people who know more than you can definitely put you into a bad place....

Maybe I need a different job strategy: instead of trying to convince
employers/clients that I know what I'm doing, appeal to them for a job on
the grounds that I want to learn how to do things RIGHT, instead of
floundering like this.....
[ SNIP ]
Darn, I was hoping that at least one thing in Java would be a simple
obvious thing that I wouldn't have to think about for a long time.

I LOVE what this language can do but it's discouraging to find that every
tiny thing needs to be thought of very carefully to keep from doing
something that will have bad consequences. COBOL, REXX and CSP were
definitely easier in that regard ;-) But so much more limited too!
[ SNIP ]

Download the source for some tight, top-notch open-source projects.
*That* is your mentor. Mentors, really, because even with just a few
decent-sized OSS projects to review you'll be exposed to the work of
dozens of programmers. You can ask for recommendations here - my first
one would be JSF 2 from https://javaserverfaces.dev.java.net/.

At this stage of the game lots of rethinking isn't a bad thing. But pick
your battles - implementation of constants isn't exactly critical. You
could in fact go with a standalone constants class, each constant being
a public static final, named the way you describe, and it's not going to
be a serious problem. It's not optimal for the reasons that others have
suggested, but quite frankly it's not a big deal.

My recommendation is, back off a bit right now from trying to write a
perfect application. Look at others' high-quality source, and learn from
it. Start reading some good articles on OOP design - you need to know OO
basics before you can have a hope of writing decent OO code.

And food for thought: you mention "bad consequences". Well, can you list
what bad consequences might be? That can be an illuminating starting
point for figuring out how you would prevent those from occurring.
Unless you know what it is that you're trying _not_ to do then you're
adrift. For example, this kind of thinking along with some readings in
OPP design would have let you figure out the answers that you've been
given in this thread, which is a lot better than being spoonfed. :)

AHS
 
R

Roedy Green

Is there any reason NOT to put _all_ of the constants used throughout the
project in FooConstants? Or is it wiser to only move something to a
XXXConstants class if it is used in more than one class?

I have a class called Config for all the constants you might
reasonably want to tweak when porting the code to a slightly different
project. For things like Regex expressions, which can be thought of
as part of the code, I find it better to put them in the sole class
where they are used.

As a general rule, make things private used in but a single class.
Make things default used in but a single project.
--
Roedy Green Canadian Mind Products
http://mindprod.com

Beauty is our business.
~ Edsger Wybe Dijkstra (born: 1930-05-11 died: 2002-08-06 at age: 72)

Referring to computer science.
 
A

Arne Vajhøj

I have a class called Config for all the constants you might
reasonably want to tweak when porting the code to a slightly different
project. For things like Regex expressions, which can be thought of
as part of the code, I find it better to put them in the sole class
where they are used.

Maybe you should read the thread.

Arne
 
R

Rhino

Lew said:
Rhino said:
obvious thing that I wouldn't have to think about for a long time.

I LOVE what this language can do but it's discouraging to find that
every tiny thing needs to be thought of very carefully to keep from
doing something that will have bad consequences. COBOL, REXX and CSP
were definitely easier in that regard ;-) But so much more limited
too!

Java is no different from other languages in this regard. The kind of
"think[ing] about for a long time" to which you refer is universal to
programming, not specific to Java.
That's the second time I've seen YAGNI in the last few days but I
still don't know what it means. I'm guessing it's something like
YMMV, Your Mileage May Vary?

The acronym was explained to you when you asked before. By more than
one. Why did you ignore the answers?

I only used the acronym because I "knew" you knew what it meant by
now.

There's really no point in answering questions for someone who ignores
the answers.

Now go google it, for Chrissake!

Sheesh.

Hey, we've got a LOT of threads going here and most of them have umpteen
subthreads and side discussions so it's a serious challenge keeping up
with it all. I'm already spending most of each day trying to monitor the
replies so that we finally get to something like a resolution. Forgive me
for missing some things....
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Similar Threads

Placement of Constants - again 13
Div placement 2
Constants? 4
need to count constants names in vhdl 0
Class Constants - pros and cons 46
placement new overhead 12
I'm tempted to quit out of frustration 1
Placement new[] 5

Members online

No members online now.

Forum statistics

Threads
473,769
Messages
2,569,580
Members
45,054
Latest member
TrimKetoBoost

Latest Threads

Top