Created
September 20, 2016 19:49
-
-
Save spareslant/62e3e749685e74fb86d158a6ef44526d to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
class OuterClass { | |
private String outerClassPrivateInstanceVar = "outerClassPrivateInstanceVar"; | |
public static String outerClassPublicStaticVar = "outerClassPublicStaticVar"; | |
public String outerClassPublicInstanceVar = "outerClassPublicInstanceVar"; | |
void outerClassInstanceMethod() { | |
System.out.println("Inside outerClassInstanceMethod."); | |
} | |
static void outerClassStaticMethod() { | |
System.out.println("Inside outerClassStaticMethod."); | |
} | |
// NON-STATIC Inner class | |
class InnerClass { | |
// Non-static innerClass cannot have static members. Following will not work. | |
// static String InnerClassStaticVar = "InnerClassStaticVar"; | |
public void innerClassMethod() { | |
System.out.println("Inside innerClassMethod."); | |
} | |
public void innerClassAccessOuterClassVars() { | |
System.out.println(outerClassPrivateInstanceVar); | |
System.out.println(outerClassPublicInstanceVar); | |
System.out.println(outerClassPublicStaticVar); | |
} | |
} | |
// STATIC Inner class | |
static class InnerClassStatic { | |
// Following is allowed in Static InnerClass but not in non-static inner class. | |
static String StaticInnerClassStaticVar = "StaticInnerClassStaticVar"; | |
String InnerClassStaticInstanceVar = "InnerClassStaticInstanceVar"; | |
public void innerClassStaticMethod() { | |
System.out.println("Inside InnerClassStatic."); | |
} | |
public void innerClassStaticAccessOuterClassVars() { | |
// Following will not work. Beacuse InnerClassStatic is like static member inside OuterClass | |
// and static members/methods can never access instance members. | |
//System.out.println(outerClassPrivateInstanceVar); | |
//System.out.println(outerClassPublicInstanceVar); | |
System.out.println(outerClassPublicStaticVar); | |
} | |
} | |
// Local Inner Class inside Instance method. | |
void outerClassInstanceMethodForLocalClass() { | |
// Local Inner Classes cannot be private, protected, public and static. Because inside method | |
// these keywords have no sense. We don't use these words inside methods. | |
class LocalClassInInstanceMethod { | |
// Static members are not allowed in Local Inner classes defined inside instance method. | |
// Following will not work. | |
//static String LocalClassInInstanceMethodStaticVar = "LocalClassInInstanceMethodStaticVar"; | |
void localClassInInstanceMethod_instanceMethod() { | |
System.out.println("Inside localClassInInstanceMethod_instanceMethod."); | |
} | |
} | |
LocalClassInInstanceMethod localClassInInstanceMethodObj = new LocalClassInInstanceMethod(); | |
localClassInInstanceMethodObj.localClassInInstanceMethod_instanceMethod(); | |
} | |
// Local Inner Class inside Static method. | |
static void outerClassStaticMethodForLocalClass() { | |
// Local Inner Classes cannot be private, protected, public and static. Because inside method | |
// these keywords have no sense. We don't use these words inside methods. | |
class LocalClassinStaticMethod { | |
// Static members are not allowed in Local Inner classes defined inside static method. | |
// Following will not work. | |
//static String LocalClassinStaticMethodStaticVar = "LocalClassinStaticMethodStaticVar"; | |
void LocalClassinStaticMethod_instanceMethod() { | |
System.out.println("Inside LocalClassinStaticMethod_instanceMethod."); | |
} | |
} | |
LocalClassinStaticMethod locallassinStaticMethodObj = new LocalClassinStaticMethod(); | |
locallassinStaticMethodObj.LocalClassinStaticMethod_instanceMethod(); | |
} | |
// Anonymous Inner classes | |
interface InnerInterface { | |
void InnerInterfaceMethod(); | |
} | |
// Anonymous inner class object defined at class member level. | |
InnerInterface anonymousClassObj = new InnerInterface() { | |
public void InnerInterfaceMethod() { | |
System.out.println("Inside InnerInterfaceMethod."); | |
} | |
}; | |
void callAnonymousObjectMethod() { | |
anonymousClassObj.InnerInterfaceMethod(); | |
} | |
// Anonymous inner class inside instance method. | |
//void anonymousInnerClassInsideMethod() { | |
OuterClass anonymousInnerClassInsideMethod() { | |
OuterClass anon = new OuterClass() { | |
void outerClassInstanceMethod() { | |
System.out.println("Inside anonymousInnerClassInsideMethod."); | |
} | |
}; | |
//anon.outerClassInstanceMethod(); | |
return anon; | |
} | |
} | |
public class InnerClassesTest { | |
public static void main(String[] args) { | |
OuterClass outerClassObj = new OuterClass(); | |
// Call to instance method using instance variable. | |
outerClassObj.outerClassInstanceMethod(); | |
// Call to static method using instance variable. In Ruby there is something called self instead of static. And | |
// self.outerClassStaticMethod in Ruby is actually a singleton method defined on a "class object (OuterClass)" and in Ruby class | |
// itself is an object. And singleton methods can be called by only object on which it is defined, in this case OuterClass object. | |
// Hence in Ruby object created by a class cannot access class method. Following is invalid in Ruby. | |
outerClassObj.outerClassStaticMethod(); | |
// NON-STATIC INNER CLASSES | |
// Creating InnerClass object. | |
System.out.println("====NON-STATIC INNER CLASSES===="); | |
OuterClass.InnerClass innerClassObj = new OuterClass().new InnerClass(); | |
innerClassObj.innerClassMethod(); | |
// Following will not work. outerClassPublicInstanceVar is not defined in InnerClass. | |
//System.out.println(innerClassObj.outerClassPublicInstanceVar); | |
innerClassObj.innerClassAccessOuterClassVars(); | |
// STATIC INNER CLASSES. | |
// Creating Static Innerclass object. You will be using Class not object. | |
System.out.println("====STATIC INNER CLASSES===="); | |
OuterClass.InnerClassStatic innerClassStaticObj = new OuterClass.InnerClassStatic(); | |
// You cannot use OuterClass object to use StaticInnerClass object. This is in contrast with creating InnerClass(non-static) object. | |
// Also normally an object can access static class fields. But Following will not work. | |
//OuterClass.InnerClassStatic innerClassStaticObj2 = outerClassObj.InnerClassStatic(); | |
// Access static inner class' static member using static inner class' object. | |
System.out.println(innerClassStaticObj.StaticInnerClassStaticVar); | |
// Access static inner class' static member using Classes directly. | |
System.out.println(OuterClass.InnerClassStatic.StaticInnerClassStaticVar); | |
// Access static inner class' instance member using static inner class' object. | |
System.out.println(innerClassStaticObj.InnerClassStaticInstanceVar); | |
// LOCAL INNER CLASSES | |
System.out.println("====LOCAL INNER CLASSES===="); | |
outerClassObj.outerClassInstanceMethodForLocalClass(); | |
outerClassObj.outerClassStaticMethodForLocalClass(); | |
OuterClass.outerClassStaticMethodForLocalClass(); | |
// ANONYMOUS INNER CLASSES | |
System.out.println("====ANONYMOUS INNER CLASSES===="); | |
outerClassObj.callAnonymousObjectMethod(); | |
// Following works because, interface InnerInterface is visible in this class as well due to default access. | |
// If inner interface in made private then following will not work. Only inner interfaces can be made private. | |
outerClassObj.anonymousClassObj.InnerInterfaceMethod(); | |
OuterClass anonymousObj = new OuterClass() { | |
void outerClassInstanceMethod() { | |
System.out.println("inside anonymousObjOfOuterClassSubClass Method."); | |
} | |
void anotherMethod() { | |
System.out.println("Inside anotherMethod."); | |
} | |
}; | |
anonymousObj.outerClassInstanceMethod(); | |
// Following will not work. Because anonymousObj is refering to actually subclass of OuterClass (in memory). But it is declared as OuterClass. | |
// That means, anonymousObj is actually a "Subclass of OuterClass" but its type is declared as OuterClass. Hence polymorphism will come in. | |
// anonymousObj being declared as superclass variable will only be able to execute methods defined in super class not in sub class. Hence | |
// following will not work. | |
//anonymousObj.anotherMethod(); | |
//Following works provided relevant lines are un-commented inside anonymousInnerClassInsideMethod instance method. | |
//outerClassObj.anonymousInnerClassInsideMethod(); | |
OuterClass out = outerClassObj.anonymousInnerClassInsideMethod(); | |
out.outerClassInstanceMethod(); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment