Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Should all methods be static if their class has no member variables

Tags:

java

static

I've just had an argument with someone I work with and it's really bugging me. If you have a class which just has methods like calculateRisk or/and calculatePrice, the class is immutable and has no member variables, should the methods be static so as not to have to create an instance of the class each time. I use the following example:

public class CalcService {
  public int calcPrice(Trade trade, Date date) {
    ...
  }
  public double calcRisk(Trade trace, Date date) {
    ...
  }
}

Should those methods be static?

like image 816
Henry B Avatar asked Mar 18 '09 14:03

Henry B


People also ask

Can all methods be static?

You can definitely make all the methods static.

Can static method use non-static members no?

No. A static method can access only static members and can not access non-static members.

When would you not use a static method?

Static methods can't be used for abstraction and inheritance. You can't declare a static method in an interface or static abstract method in an abstract class. A static method cannot access non-static class level members, not its own, nor its base class.

Why not all methods are static?

Objects are state and behavior encapsulated together. Even if the methods are the same, each instance can have its own state. If those methods are operating on instance state they will behave differently.


17 Answers

The class you describe is simply just a set of functions that operate on inputs only. It's perfectly reasonable to make such functions static methods of a class. Doing so groups them logically and eliminates possible name conflicts. The class in fact acts as a namespace and nothing more.

like image 133
sharptooth Avatar answered Oct 04 '22 11:10

sharptooth


I would say yes, but an argument could also be made in this case for just putting those methods on the Trade object.

like image 28
Eric Petroelje Avatar answered Oct 04 '22 11:10

Eric Petroelje


There is a general feeling against static classes these days, for testability reasons.

This is because static classes cannot implement an interface and so cannot be easily substituted for test classes if needed. I think that cases like this that deal with price are an excellent example of this. It is possible in future that there may be multiple ways of calculating a price, and it is nice to be able to substitute these calculators for one another as the need arises.

It may not be useful now but I see more advantages in not using a static class than using one.

like image 34
Jack Ryan Avatar answered Oct 04 '22 13:10

Jack Ryan


I would make the whole thing static.

like image 22
Otávio Décio Avatar answered Oct 04 '22 12:10

Otávio Décio


While you could use JMockit or any similar tool to mock out the static methods, my own personal choice would be to avoid statics where possible since static methods often increase coupling.

Some of the answers implies that the method is stateless, but I don't really want to see it that way. The method accepts state in form of method parameters. What if those parameters were state in an object instead?

like image 40
Magnus Avatar answered Oct 04 '22 13:10

Magnus


I would avoid making these static. Whilst at the moment that may make sense, you may in the future want to add some behaviour. e.g. at the moment you would have a default calculation engine (strategy):

CalcService cs = new CalcService();
cs.calcPrice(trade, date);

and later on you may want to add a new calculation engine:

CalcService cs = new CalcService(new WackyCalculationStrategy());
cs.calcPrice(trade, date);

If you make this class instantiatable, then you can create different instances and pass them around, instantiate on the fly etc. You can give them long-running behaviour (e.g. how many calculations involving trade X has this object done ? etc.)

like image 39
Brian Agnew Avatar answered Oct 04 '22 12:10

Brian Agnew


It is a tough call. Remember what Josh Bloch says about APIs:

APIs, like diamonds, are forever. You have one chance to get it right so give it your best.

(This may not be a public API, but if you have colleagues that are going to use this code, it effectively is an API.) If you declare those methods static, you constrain their future evolution, and incorporating state in the class will be difficult or impossible. You are going to have to live with those static method signatures. If you decide to make them non-static down the road because you need state, you are going to break the client code. I would say, when in doubt, don't make them static. That said, there is a place for static utility classes that contain a bunch of functions (e.g. calculate the area of a circle.) Your class may fall into that category.

like image 39
Julien Chastang Avatar answered Oct 04 '22 12:10

Julien Chastang


I clearly would say no.

It's much harder to change out in the future if you call static methods instead of instance ones. With instance methods it's easy to inject your service, e.g. in Java with an IoC/DI container like Guice or Spring.

like image 20
KingOfCoders Avatar answered Oct 04 '22 13:10

KingOfCoders


The answer is yes and no. It all depends on the purpose of the method behavior. For example:

  1. if these methods are simply utility methods then it makes perfect sense to make them static.

  2. If the methods represent some sort of business logic of your application (let's say... a web application) then you may want to make them as flexible as possible. In this case, they would become a simple POJO class, as instance methods. This has the not so obvious benefit that they can be converted to Spring transactional beans, or even EJB3 session beans with very little effort. It also makes the methods easier to test. You can also create interfaces for this bean and add additional aspects to it the way you need.

like image 25
Antonio Avatar answered Oct 04 '22 12:10

Antonio


If you make it static, you can't inject a different implementation easily.

There is no longer any runtime cost to calling non-static methods, so for new code avoid static as far as sensible.

OTOH, refactoring tools can replace all calls to a static method fairly easily, so it's not critical one way or another.

I don't know whether the calculation of prices or risks can vary in your domain. If there are different strategies, passing a stateless strategy implementation around may have benefits. But it's more code, and there's a good chance that YAGNI.

like image 20
Pete Kirkham Avatar answered Oct 04 '22 12:10

Pete Kirkham


Imo, they should be static. I see no reason why they shouldn't be, since instance objects would have no state, and calling the methods without instantiating would require less code and thus improved readability.

Actually, i would probably make sure the class won't be instantiated by making it abstract.

like image 24
Raibaz Avatar answered Oct 04 '22 13:10

Raibaz


if the methods need information in a Trade instance to do their work, then why aren't these methods non-static members of the Trade class?

like image 20
taglius Avatar answered Oct 04 '22 13:10

taglius


I believe that stateless methods should generally be static.

  • It's clear in the code that no object is involved
  • It avoids a meaningless constructor invocation

I can see breaking this rule for a strategy-pattern implementation, as a number of people have noted here.

like image 34
Steve B. Avatar answered Oct 04 '22 11:10

Steve B.


It depends what your goal is:

If your goal is to write as few lines of code as possible, the static approach would be the best.

If your goal is testability, we've discovered that static methods are a bugger to mock out. We, sadly, end up writing an interface, and a class for some of these just to be able to mock them out easily.

like image 24
Daniel Avatar answered Oct 04 '22 12:10

Daniel


If it is not a clearly requirement to have it as "static" I would recommend you to make them instance.

Not only because this would generate a healthy practice, but, if you're using this in production code that might change in the future, it may happen that some day you really need to change the implementation for an specific module and don't want to break the whole application only for this reason.

Again, this might not happen with your specific code, but I was once in this app with tons of classes like this ( 40 - 60 or more )

A lot of times, having these classes as statics, prevent us from changing some modules easily and causes a lot of misery and tears.

It would've been easier if I could have inject new implementations for those specific parts.

The lines of code of this app in 500k and not all of them were in java which make the refactoring harder.

If you're using this in a 1k line project, then it doesn't matter at all.

like image 22
OscarRyz Avatar answered Oct 04 '22 13:10

OscarRyz


In above answers i read the argument of not making it static for testing reasons. I do not see why, but I am not familiair with the test procedure you're using.

In our company we use unit and system testing with Junit. (org.junit) There it's no problem at all to test static methods with this test package.

So I would say: yes make them static.

(With the remark that I do not know the test procedure where testing static methods is a problem)

like image 1
michel.iamit Avatar answered Oct 04 '22 12:10

michel.iamit


I recently came across same problem. I was usnig static method. This method basically returns the folder path I need to save all the user defined settings. Now the problem is that I need to write a test case that basically wipes out everything from the folder. I'd definitely not want to delete actual files and therefore I'd want that method to return something else. Yakes .... I can't casue I can't mock the method as it's static. Left with no luck but to change it to a not static method and have the class implement the interface with that method. Then I can easily mock that interface and have the method return any path I want.

End result. Making it a not static gives you more functionality. Make class Singleton and you have everything a static does for you plus loosely coupling.
like image 1
Sheraz Avatar answered Oct 04 '22 11:10

Sheraz