Following is the code I tried to run, the output was Good. So, we can use a variable of interface implemented by a class?
interface IDummyInterface {
public String TYPE = "Good";
}
class Test implements IDummyInterface {
}
public class MyApplication {
public static void main(String[] args) {
System.out.println(Test.TYPE);
}
}
Any class that implements an interface, and any class that extends a class that implements that interface, inherits all of that interfaces variables. No matter how you declare the variables in the interface, all interface variables are public static final, which is why you can access them with just the class name and not an instance of the class.
Test implements IDummyInterface.so all variables of IDummyInterface are inherited
The variable is actually static final. And since it is static, it follows the same rules as all static variables declared in classes, which are accessible through any other class that inherit from it. In that regard interfaces behave like classes.
class StaticTestParent { public static final int VALUE = 1; }
class StaticTestChild extends StaticTestParent { }
static {
System.out.println(StaticTestChild.VALUE);
}
Related
We have an interface and class with no relation each having methods with same signature. These can be related to a class which would compile fine.
interface A {
void test();
}
class B {
public void test() {
System.out.println("Test");
}
}
public class MultipleLevelInheritance extends B implements A {
public static void main(String[] args) {
new MultipleLevelInheritance().test();
}
}
But when we do the same with the a variable its causing ambiguity.
interface A {
int a = 10;
}
class B {
public static int a = 9;
}
public class MultipleLevelInheritance extends B implements A {
public static void main(String[] args) {
System.out.println(a); //The field a is ambiguous
}
}
Even if we keep a as final in B, its still causing the error. Why is that valid for methods and invalid for variables?
When you implement an interface, all variables are inherited in the class. So, when you extend a class and implements the interface, it will have two declaration of variable a. Hence you are getting ambiguity error.
But when it comes to methods, when you implement the interface, you are expected to provide the implementation of the methods defined in interface. In your example, this implementation is provided by class B. Therefore there is no error.
Your class MultipleLevelInheritance is implementing an interface and extending a class, and both have the same property name (a),when you call a in MultipleLevelInheritance, Java is not able to determine if the variable refers to A.a or B.a. you just need to prefix it.
I am having issues extending an inner class with a generic abstract class.
I get an Non-static field cannot be referenced from a static context which is odd because the class itself is static, not necessarily the field value.
This is basically what I have:
// AbstractFoo.java
public abstract class AbstractFoo extends FrameLayout {
// Some logic
}
// AbstractBar.java
public abstract class AbstractBar<T> {
int someNumber;
// Some logic
}
// Foo.java
public class Foo extends AbstractFoo {
// Some logic
// Foo.InnerFoo.java
public static class InnerFoo extends AbstractBar<InnerFoo> {
public InnerFoo() {
super.someNumber = 5; // Compiler error HERE
}
}
}
For some reason I cannot access someNumber from InnerFoo. From my understanding this shouldn't cause any issues. The classes I'm extending btw is from an external library.
This is also all done with Android where minimum SDK is 24.
Thanks for the help!
The fields defined in your classes do not have an explicit access modifier which would use the default access modifier and limit the visibility to classes within the same package.
You should make the fields in AbstractBar as protected -
public abstract class AbstractBar<T> {
protected int someNumber;
}
I know the difference between all the access modifiers in Java. However, someone asked me a very interesting question that I struggled to find the answer to: What is the difference between a private interface and a public interface in Java, in particular, how it is used as a class member? Any help would be greatly appreciated.
I believe we all know the use of public interface, so I would mention the point of private/protected interface here.
Interfaces can be members of class definitions and can be declared private or protected there.
public class Test {
private interface Sortable {
}
protected interface Searchable {
}
}
Example 1: -- Source
public class PrivateInterface {
private interface InnerInterface {
void f();
}
private class InnerClass1 implements InnerInterface {
public void f() {
System.out.println("From InnerClass1");
}
}
private class InnerClass2 implements InnerInterface {
public void f() {
System.out.println("From InnerClass2");
}
}
public static void main(String[] args) {
PrivateInterface pi = new PrivateInterface();
pi.new InnerClass1().f();
pi.new InnerClass2().f();
}
}
/* Output:
From InnerClass1
From InnerClass2
*/
It's the interface itself that can be package-private, not the methods
in it. You can define an interface that can only be used (by name)
within the package it's defined in, but its methods are public like
all interface methods. If a class implements that interface, the
methods it defines must be public. The key thing here is that it's the
interface type that isn't visible outside the package, not the
methods.
The public, private, and protected access modifiers on an interface mean the same thing that they mean on a class. I typically see these modifiers used on an interface that is nested in a class. Something like this:
//: interfaces/RandomWords.java
// Implementing an interface to conform to a method.
package interfaces;
public class PrivateInterface {
private interface InnerInterface {
void f();
}
private class InnerClass1 implements InnerInterface {
public void f() {
System.out.println("From InnerClass1");
}
}
private class InnerClass2 implements InnerInterface {
public void f() {
System.out.println("From InnerClass2");
}
}
public static void main(String[] args) {
PrivateInterface pi = new PrivateInterface();
pi.new InnerClass1().f();
pi.new InnerClass2().f();
}
}
An interface declaration may include these access modifiers:
public protected private abstract static strictfp
public: If an interface type is declared public,then it can be accessed by any code.
protected/private: The access modifiers protected and private pertain only to member interfaces within a directly enclosing class declaration. A member interface is an interface whose declaration is directly enclosed in another class or interface declaration.
static: The access modifier static pertains only to member interfaces, not to top level interfaces.
abstract: Every interface is implicitly abstract. This modifier is obsolete and should not
be used in new programs.
strictfp: The effect of the strictfp modifier is to make all float or double expressions
within the interface declaration be explicitly FP-strict.
Ref: Java Language and Virtual Machine Specifications
Can we have a class inside an interface which has different methods of the interface implemented in it. I have a doubt here that why Java allows writing Inner classes inside interfaces and where can we use it.
In the program below I have written a class inside Interface and implemented the methods of the interface. In the implementation class of the interface I have just called the inner class methods.
public interface StrangeInterface
{
int a=10;int b=5;
void add();
void sub();
class Inner
{
void add()
{
int c=a+b;
System.out.println("After Addition:"+c);
}
void sub()
{
int c=a-b;
System.out.println("After Subtraction:"+c);
}
}
}
abstract public class StrangeInterfaceImpl implements I {
public static void main(String args[])
{
StrangInterface.Inner i=new StrangeInterface.Inner();
i.add();
i.sub();
}
}
You can define a class inside an interface. Inside the interface, the inner class is implicitly public static.
From JLS Section 9.1.4:
The body of an interface may declare members of the interface, that is, fields (§9.3), methods (§9.4), classes (§9.5), and interfaces (§9.5).
From JLS Section 9.5:
Interfaces may contain member type declarations (§8.5).
A member type declaration in an interface is implicitly static and public. It is permitted to redundantly specify either or both of these modifiers.
The only restriction on the inner class defined inside the interface or any other class, for that matter, is that, you have to access them using the enclosing member name.
Apart from that, there is no relation between them. The inner class will result in completely a different class file after compilation.
For e.g., if you compile the following source file:
interface Hello {
class HelloInner {
}
}
Two class files will be generated:
Hello.class
Hello$HelloInner.class
Can we have a class inside an interface which has different methods of the interface implemented in it.
IMHO But interfaces are not meant to for that purpose.
If you write inner class in an interface it is always public and static.
It's equivalent to
public interface StrangeInterface
{
public static class Inner{
}
and the variable inside the interface also explicitly public static variables.
An interface might provide its own implementation as a default.
Note that unless you declare the inner class implements the interface, there's no relation between the two other than it's an inner class. When a class is very tightly related to the interface this isn't intrinsically unreasonable, although I'd be suspicious it's a generally-useful pattern.
to summarize "where can we use it" by defining a class inside an interface:
1. to provide default implementation for an interface
2. if argument or return type for interface method/s is class
w.r.t your code
interface StrangeInterface {
int a = 10;
int b = 5;
void add();
void sub();
class Inner implements StrangeInterface {
public void add() {
int c = a + b;
System.out.println("After Addition:" + c);
}
public void sub() {
int c = a - b;
System.out.println("After Subtraction:" + c);
}
}
}
class MyTest implements StrangeInterface {
public void add() {
System.out.println("My own implementation for add : " + (a +b));
}
public void sub() {
System.out.println("My own implementation for sub : " + (a- b));
}
}
public class StrangeInterfaceImpl {
public static void main(String args[]) {
StrangeInterface.Inner i = new StrangeInterface.Inner(); // calling default implementation
i.add();
i.sub();
MyTest t = new MyTest(); // my own implementation
t.add();
t.sub();
}
}
I have abstract class and interface like this
abstract class ParentClass
{
int VALUE;
public abstract void display();
public void display2()
{
System.out.println("this is abstract class method");
}
}
interface parentInterface
{
int VALUE=88;
abstract void display();
void display2();
}
the child class extends and implements the above like following
class ChildClass extends ParentClass implements parentInterface
{
ChildClass()
{
super.VALUE=0;
//VALUE=0; //<=will give ambiguous property
}
#Override
public void display()
{
System.out.println("Current Class-"+this.getClass());
System.out.println("Integer value-"+super.VALUE);
}
public void display2()
{
//to call the method of abstract class
//call by using super.display2();
System.out.println("this is implemented method");
}
}
So, my question is How can i access interface VALUE variable in ChildClass ??
You can access the VALUE from interface using parentInterface.VALUE as variables in interfaces are public static final by default.
And the abstract class's VALUE can be accessed using this.VALUE as it is a member variable.
variables in interface are implicitly public static final.
static - because Interface cannot have any instance.
final - the value assigned to the interface variable is a true constant that cannot be re-assigned by program code.
Interface variables can be accessed using <Interface>.VALUE whereas the variables from the parent class are inherited and hence can be accessed using this.VALUE.
if any subclass class is implementing an interface which has instance
members and if both subclass and interface are in the same package
then that static members can be accessed from the child class without
even using the Interface name.
Thats why you are getting the ambiguous error. Please put Interface in some other package and then it should not show such an error else you will have to access it like super.VALUE