Tell me more ×
Programmers Stack Exchange is a question and answer site for professional programmers interested in conceptual questions about software development. It's 100% free, no registration required.

What's the difference between the two UpdateSubject methods below? I felt using static methods is better if you just want to operate on the entities. In which situations should I go with non-static methods?

public class Subject
{
    public int Id {get; set;}
    public string Name { get; set; }

    public static bool UpdateSubject(Subject subject)
    {
        //Do something and return result
        return true;
    }
    public bool UpdateSubject()
    {
        //Do something on 'this' and return result
        return true;
    }
}

I know I will be getting many kicks from the community for this really annoying question but I could not stop myself asking it.

Does this become impractical when dealing with inheritance?

Update:
Its happening at our work place now. We are working on a 6 month asp.net web application with 5 developers. Our architect decided we use all static methods for all APIs. His reasoning being static methods are light weight and it benefits web applications by keeping server load down.

share|improve this question
6  
Rich Hickey would encourage something non-idiomatic like that (all static methods). If you like a functional style, you might as well use a functional language ;) Not everything in software is best modeled as an object. – Job Aug 3 '11 at 2:29
9  
@Job: I don't really see how this is functional - it's procedural. – Aaronaught Aug 3 '11 at 4:16
2  
@Job: This class is not immutable. – Aaronaught Aug 4 '11 at 2:58
1  
@Job: I'm still not sure why it rang a bell; in a functional language these would be functions, not static methods belonging to a data type. And the functions would never mutate state, so you wouldn't see names like "Update". I get your essential point, totally: OOP isn't the only useful paradigm. However, this isn't functional or even really resembling functional, it's just really bad OOP. – Aaronaught Aug 4 '11 at 3:28
2  
@DonalFellows: Of course you can, C# and F# are both mixed-paradigm. But the fact remains, static methods != functional programming. FP means passing/chaining functions, immutable data types, avoidance of side-effects, etc. That's completely opposite of what the code snippet in the OP does. – Aaronaught Jan 22 '12 at 19:44
show 8 more comments

7 Answers

up vote 43 down vote accepted

I'll go with the most obvious problems of static methods with explicit "this" parameters:

  1. You lose virtual dispatch and subsequently polymorphism. You can never override that method in a derived class. Of course you can declare a new (static) method in a derived class, but any code that accesses it has to be aware of the entire class hierarchy and do explicit checking and casting, which is precisely what OO is supposed to avoid.

  2. Sort of an extension of #1, you can't replace instances of the class with an interface, because interfaces (in most languages) can't declare static methods.

  3. The unnecessary verbosity. Which is more readable: Subject.Update(subject) or just subject.Update()?

  4. Argument checking. Again depends on the language, but many will compile an implicit check to ensure that the this argument is not null in order to prevent a null reference bug from creating unsafe runtime conditions (kind of a buffer overrun). Not using instance methods, you'd have to add this check explicitly at the beginning of every method.

  5. It's confusing. When a normal, reasonable programmer sees a static method, he is naturally going to assume that it doesn't require a valid instance (unless it takes multiple instances, like a compare or equality method, or is expected to be able to operate on null references). Seeing static methods used this way is going to make us do a double or perhaps triple take, and after the 4th or 5th time we are going to be stressed and angry and god help you if we know your home address.

  6. It's a form of duplication. What actually happens when you invoke an instance method is that the compiler or runtime looks up the method in the type's method table and invokes it using this as an argument. You are basically re-implementing what the compiler already does. You're violating DRY, repeating the same parameter again and again in different methods when it's not needed.

It's hard to conceive of any good reason to replace instance methods with static methods. Please don't.

share|improve this answer
1  
+1 for your final line alone. I wish a lot more people would think "instance method" before they think "static method". – Stu Jan 22 '12 at 20:41

You've pretty much described exactly how you do OOP in C, in which only static methods are available, and "this" is a struct pointer. And yes, you can do run time polymorphism in C by specifying a function pointer during construction to be stored as one element of the struct. Instance methods available in other languages are just syntactic sugar that essentially does exactly the same thing under the hood. Some languages, like python, are halfway between, where the "self" parameter is explicitly listed, but special syntax for calling it handles inheritance and polymorphism for you.

share|improve this answer
FWIW, with C you can do virtual dispatch like this: obj->type->mthd(obj, ...); and that's substantially similar to what happens with virtual dispatch in other languages (but behind the scenes). – Donal Fellows Jan 22 '12 at 15:44

The problem with static method comes the moment you need a sub-class.

Static methods cannot be overridden in sub-classes, hence your new classes cannot provide new implementations of the methods, making them less useful.

share|improve this answer
1  
This isn't necessarily a problem. Some languages provide other mechanisms (non-virtual methods in C++ and C#) for accomplishing the same thing intentionally - C# even provides "sealed" methods to further extend this idea! Obviously, you wouldn't do this just for the heck of it, but it's a good technique to be aware of... – Shog9 Aug 2 '11 at 23:50
@Steve, that is not replacing, as you can still call both methods directly. – user1249 Aug 3 '11 at 9:49
@Steve, in Java static methods cannot be overridden. – user1249 Aug 3 '11 at 21:26
@Thorbjørn - first, the question isn't tagged Java, or any other specific OOP language. More importantly, I didn't say you could override a static member function. I was trying to use an analogy to make a point. As I clearly failed, comments deleted. – Steve314 Aug 3 '11 at 21:47
2  
In a sense, these are still "new implementations of methods". Just not in the standard OOP sense. This feels a bit like I'm saying "your wording ain't perfect either, nur-nur-na-nur-nur" ;-) – Steve314 Aug 3 '11 at 21:59
show 3 more comments

If you declare a method static, you do not have to instantiate an object from the class (using the new keyword) to execute the method. However, you can't refer to any member variables unless they are also static, in which case those member variables belong to the class, not a specific instantiated object of the class.

Put another way, the static keyword causes a declaration to be part of the class definition, so it becomes a single reference point across all instances of the class (objects instantiated from the class).

It follows, then, that if you want multiple running copies of your class, and you don't want the state (member variables) to be shared among all of your running copies (i.e. each object holds its own unique state), then you cannot declare those member variables static.

In general, you should use static classes and methods only when you are creating utility methods that accept one or more parameters, and return an object of some sort, without any side effects (i.e. changes to state variables in the class)

share|improve this answer
1  
I thin the OP understands what static means, he is asking why not just declare everything as static. – Ed S. Aug 2 '11 at 23:31
He is passing in an instance of Subject - but as an explicit parameter, instead of the implicit this parameter. – Steve314 Aug 2 '11 at 23:33
Well, yeah... but I don't see your point I suppose. – Ed S. Aug 2 '11 at 23:35
@Ed - only that you can do pretty much anything through an explicit parameter that you could through an implicit this parameter. There's differences in expectations, but outside of inheritence, there's no real difference in what you can do. For example, those non-static members can be accessed - via the explicit parameter. – Steve314 Aug 2 '11 at 23:59
I was operating under the assumption that you could not get at private members of the argument in C# even through a static method declared in the same class (as you can in C++). Not sure why I thought that, but I was wrong. – Ed S. Aug 3 '11 at 0:26

You're basically defeating the whole point of objects when you do this. There's a good reason we have pretty much shifted from procedural code to object oriented code.

I would NEVER declare a static method that took the class type as a parameter. That just makes the code more complex for no gain.

share|improve this answer
1  
You might do it if you were passing an object to a static method, and returning a new object. Functional programmers do this all the time. – Robert Harvey Aug 3 '11 at 3:50

The reason people argue that 'static methods show bad design' isn't necessarily due to the methods, it's actually static data, implicit or explicit. By implicit I mean ANY state in the program that isn't contained in the return value(s) or parameters. Modifying state in a static function is a throwback to procedural programming. However if the function does not modify state, or delegates state modification to component object functions, it's actually more a functional paradigm than procedural.

If you're not changing state, static methods and classes can have many benefits. It makes it much easier to ensure a method is pure, and thus free of side effects and any errors are fully reproducible. It also ensures that different methods in multiple applications using a shared library can be assured they will get the same results given the same input, making both error tracking and unit testing much easier.

Ultimately there's no difference in practice between oversized objects commonly seen such as 'StateManager' and static or global data. The benefit of static methods used correctly is they can indicate the author's intent to not modify state to later revisers.

share|improve this answer
1  
Your statement "...is a throwback to procedural programming..." makes me think that you consider it so bad, I guess it is part of OO in a sense. – Emmad Kareem Feb 29 '12 at 10:00
making ... unit testing much easier. No it won't. It makes it makes any code that calls static methods impossible to unit test, since you can't isolate it from the static method. A call to a static method becomes a hardcoded dependency to that class. – StuperUser Dec 19 '12 at 13:21

Depending on the language and what you are trying to do, the answer may be that there's not a lot of difference, but the static version has a bit more clutter.

As your example syntax suggests Java or C#, I think Thorbjørn Ravn Andersen is right to point out the overriding (with late binding) issue. With a static method, there is no "special" parameter for late binding to be based on, so you can't have late binding.

In effect, a static method is just a function in a module, that module having the same name as the class - it isn't really an OOP method at all.

share|improve this answer

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.