views:

708

answers:

6

hi why cant we have static method in an inner class

and if i make inner class static it works why so

+10  A: 

Because an inner class is implicitly associated with an instance of it's outer class, it cannot define any static methods itself. Since a static nested class cannot refer directly to instance variables or methods defined in its enclosing class, it can use them only through an object reference, it's safe to declare static methods in a static nested class.

Bill the Lizard
Actually that's not entirely true. An inner class can define static final constants.
cletus
@cletus: Thanks. I changed "member" to "method" so it should be correct now.
Bill the Lizard
+1  A: 

An inner class is something completely different from a static nested class although both are similar in syntax. Static nested classes are only a means for grouping whereas inner classes have a strong association - and access to all values of - their outer class. You should be sure why you want to use an inner class and then it should come pretty natural which one you have to use. If you need to declare a static method it's probably a static nested class you want anyway.

Benedikt Eger
Benedikt, what do you mean when you say "static nested classes are only a means to grouping" ?
Ankur
@Ankur > think "namespace"
Gregory Pakosz
A: 

You are allowed static methods on static nested classes. For example

public class Outer {

  public static class Inner {

    public static void method() {

    }
  }
}
mR_fr0g
+2  A: 

I have a theory, which may or may not be correct.

First, you should know some things about how inner classes are implemented in Java. Suppose you've got this class:

class Outer {
    private int foo = 0;
    class Inner implements Runnable {
        public void run(){ foo++; }
    }
    public Runnable newFooIncrementer(){ return new Inner(); }
}

When you compile it, the generated bytecode will look as if you wrote something like this:

class Outer {
    private int foo = 0;
    static class Inner implements Runnable {
        private final Outer this$0;
        public Inner(Outer outer){
            this$0 = outer;
        }
        public void run(){ this$0.foo++; }
    }
    public Runnable newFooIncrementer(){ return new Inner(this); }
}

Now, if we did allow static methods in non-static inner classes, you might want to do something like this.

class Outer {
    private int foo = 0;
    class Inner {
        public static void incrFoo(){ foo++; }
    }
}

... which looks fairly reasonable, as the Inner class seems to have one incarnation per Outer instance. But as we saw above, the non-static inner classes really are just syntactic sugar for static "inner" classes, so the last example would be approximately equivalent to:

class Outer {
    private int foo = 0;
    static class Inner {
        private final Outer this$0;
        public Inner(Outer outer){
            this$0 = outer;
        }
        public static void incrFoo(){ this$0.foo++; }
    }
}

... which clearly won't work, since this$0 is non-static. This sort of explains why static methods aren't allowed (although you could make the argument that you could allow static methods as long as they didn't reference the enclosing object), and why you can't have non-final static fields (it would be counter-intuitive if instances of non-static inner classes from different objects shared "static state"). It also explains why final fields are allowed (as long as they don't reference the enclosing object).

gustafc
+2  A: 

There's not much point to allowing a static method in a non-static inner class; how would you access it? You cannot access (at least initially) a non-static inner class instance without going through an outer class instance. There is absolutely no static way to create a non-static inner class.

For an outer class Outer, you can access a static method test() like this:

Outer.test();

For a static inner class Inner, you can access its static method innerTest() like this:

Outer.Inner.innerTest();

However, if Inner is not static, there is now no static way to reference the method innertest. Non-static inner classes are tied to a specific instance of their outer class.

If you actually need static methods on a non-static inner class, then you probably need to rethink your design.

Eddie
+2  A: 

suppose there are two instances of outer class & they both have instantiated inner class.Now if inner class has one static member then it will keep only one copy of that member in heap area.In this case both objects of outer class will refer to this single copy & they can alter it together.This can cause "Dirty read" situation hence to prevent this Java has applied this restriction.Another strong point to support this argument is that java allows final static members here, those whose values can't be changed from either of outer class object. Please do let me if i am wrong.

Malay