This question already has answers here:
What is a raw type and why shouldn't we use it?
(16 answers)
Closed 4 years ago.
I have this code:
public interface Interface1{
void interfaceMethod1();
}
public class Class1<T extends Class0&Interface1>{
private T field;
public T getField(){
return field;
}
}
When I invoke class1.getField().interfaceMethod1(), where class1 is Class1 instance, I see error "Cannot resolve method".
I want to define class with generic field which will include methods from Class0 and Interface1.
Assume we have next definitions:
public interface Interface1 {
void interfaceMethod1();
}
public class Class0 {
}
public class Class2 extends Class0 implements Interface1 {
#Override
public void interfaceMethod1() {
}
}
public class Class1<T extends Class0 & Interface1> {
private T field;
public T getField() {
return field;
}
}
When you have
Class1 class1 = new Class1();
class1.getField().interfaceMethod1();
it is called type erasure. It means all generic arguments assumed to be Object, so class1.getField() return Object which lack of interfaceMethod1 method.
To fix that you should do this:
Class1<Class2> class1 = new Class1<>();
class1.getField().interfaceMethod1();
Now everything compiles fine.
Related
This question already has answers here:
What is the difference between public, protected, package-private and private in Java?
(30 answers)
Closed 7 years ago.
Is there any security/access difference when making a package access level abstract class's non-static methods public vs making them protected? Only classes from within the same package that extend the abstract class can access the non-static methods anyway right? So, does it matter whether those non-static methods are public or protected since the abstract class itself places restrictions on who can extend it?
abstract class MyClass {
protected void myFunction(){
System.out.println("Only child classes can print this");
}
}
abstract class MyClass {
public void myFunction(){
System.out.println("Still, only child classes can print this");
}
}
The public abstract method will be accessible in the other package where as the protected abstract method can not be accessed. Check the example below.
An abstract class with both public and protected abstract methods
package package1;
public abstract class MyClass {
abstract protected String method1();
abstract public String method2();
}
Another package which extends the class and implements the abstract class.
package package2;
import package1.MyClass;
public class MyClassImpl extends MyClass {
#Override
protected String method1() {
return "protected method";
}
#Override
public String method2() {
return "public method";
}
}
Main class for accessing the abstract method.
package package2;
import package1.MyClass;
public class MainClass {
static MyClass myClass = new MyClassImpl();
public static void main(String[] args) {
System.out.println(myClass.method1()); // This is compilation error.
System.out.println(myClass.method2());
}
}
This question already has answers here:
Calling super super class method
(12 answers)
Closed 7 years ago.
Let's say I have a base class called Vehicle, and another class called Car that extends it. Finally I have a class Luxury that extends Car.
I know I can use the keyword super to invoke a base-class method. How do I invoke a method of the Vehicle class from Luxury?
There is no builtin mechanism for this. You have to create a helper method in the first subclass.
public class A {
public void myMethod() { ... }
}
public class B extends A {
public void myMethod() {
// something
}
protected void myMethodA() {
super.myMethod();
}
}
public class C extends B {
public void myMethod() {
myMethodA();
}
}
This question already has answers here:
Instantiating a generic class in Java [duplicate]
(10 answers)
Closed 8 years ago.
Here's the code:
package Fabrika.Trake;
import Vozila.*;
public class Traka<T extends Vozilo> extends Thread
{
protected int vrijemeRada;
...
#Override
public void run()
{
while(true)
{
//I want to create the object here
}
}
}
Now, let's say I have a class called Auto which extends Vozilo.
I'd like to know if there is a way of constructing an object of type T without using reflection. Something like:
T object = new T();
This, of course, is completely incorrect, but it just serves as an illustration of what I'd like to do. :)
Use a type token.
public class Traka<T extends Vozilo> extends Thread
{
private Class<T> type;
protected int vrijemeRada;
...
public Traka(Class<T> type) {
this.type = type;
}
#Override
public void run()
{
while(true)
{
//I want to create the object here
T object = type.newInstance();
}
}
}
This works - of course - only with constructors that have a known number of arguments. My example uses a no-arg constructor.
And: Do not extend Thread! Implement Runnable instead. And then uses those runnables, wherever you need them.
You can't do this with just the generic type T.
To create an instance you need a Class instance.
E.g.:
public class Traka<T extends Vozilo> extends Thread
{
protected int vrijemeRada;
...
private Class<T> type;
public Traka(Class<T> type) {
this.type = type;
}
#Override
public void run()
{
while(true)
{
T newInstance = type.newInstace(); // this uses the default constructor
}
}
}
Usage:
Traka<Auto> autoTraka = new Traka(Auto.class);
The problem is that the generic type information T is erased at runtime. Therefore you need a Class instance to represent the type at runtime.
There is a special pattern for this: pass Class instance to the constructor of Traka, store it in a private variable, and the use that class to instantiate new objects, like this:
public class Traka<T extends Vozilo> extends Thread {
private Class<T> theClass;
public Traka(Class<T> theClass) {
this.theClass = theClass;
}
...
#Override
public void run() {
while(true) {
T inst = theClass.newInstance();
}
}
}
Note: In case you were wondering why Class became parameterized in Java 5, the pattern above is the answer.
This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
Create instance of generic type in Java?
I got these classes
public abstract class Base {
public String Id = "originalId";
}
public class InstanceOfBase extends Base {
public void setString(String test) {
this.Id = test;
}
}
public class UseIt {
public Test<InstanceOfBase> test = new Test<InstanceOfBase>();
public void run() {
InstanceOfBase instanceOfBase = test.createMe();
System.out.println(instanceOfBase.Id);
}
}
public abstract class Test<E extends Base> {
public E createMe() {
// How do I do this?
return new E();
}
}
The code above does not compile because it does not know how to create E. how can I achieve this?
When I invoke the run method, I expect it should print "originalId".
Unfortunately you cannot create classes from generic types in java. But you can do as Justin Rudd suggested in this thread and write:
public E createMe(Class<E> clazz)
{
return clazz.newInstance();
}
So you use the class archetype to create a new instance. Invoking it could be:
InstanceOfBase instanceOfBase = test.createMe(test.getClass)
This question already has answers here:
Determine if a Class implements a interface in Java
(5 answers)
Closed 3 years ago.
How to check if some class implements interface?
When having:
Character.Gorgon gor = new Character.Gorgon();
how to check if gor implements Monster interface?
public interface Monster {
public int getLevel();
public int level = 1;
}
public class Character {
public static class Gorgon extends Character implements Monster {
public int level;
#Override
public int getLevel() { return level; }
public Gorgon() {
type = "Gorgon";
}
}
}
Is the method getLevel() overridden in Gorgon correctly, so it can return level of new gor created?
For an instance
Character.Gorgon gor = new Character.Gorgon();
Then do
gor instanceof Monster
For a Class instance do
Class<?> clazz = Character.Gorgon.class;
Monster.class.isAssignableFrom(clazz);
Use
if (gor instanceof Monster) {
//...
}
In general for AnInterface and anInstance of any class:
AnInterface.class.isAssignableFrom(anInstance.getClass());
If you want a method like public void doSomething([Object implements Serializable]) you can just type it like this public void doSomething(Serializable serializableObject). You can now pass it any object that implements Serializable but using the serializableObject you only have access to the methods implemented in the object from the Serializable interface.