I'm struggling to make a mapping from class B to any subclass of A. See code below. It seems it is not possible with ModelMapper, since it ignores converter if it is not exact match. Could you recommend some similar library that is capable of this? Or any recommendation how to do similar behavior, without specifying all possible subclasses explicitly. Thanks a lot.
package com.randakm.p2plibrary.service.main;
import org.modelmapper.Converter;
import org.modelmapper.ModelMapper;
import org.modelmapper.spi.MappingContext;
public class ServiceMain {
/**
* #param args
*/
public static void main(String[] args) {
ModelMapper mapper = new ModelMapper();
mapper.addConverter(new B2AConverter());
B b = new B();
b.b = "some value";
A a = mapper.map(b, AA.class);
System.out.println("a: "+a.a); // I expect this to have the value from b
}
}
abstract class A {
String a;
}
class AA extends A {
String aa;
}
class AAA extends A {
String aaa;
}
class B {
String b;
}
class B2AConverter implements Converter<B, A> {
#Override
public A convert(MappingContext<B, A> context) {
B b = context.getSource();
A a;
try {
a = context.getDestinationType().newInstance();
a.a = b.b;
return a;
} catch (InstantiationException | IllegalAccessException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return null;
}
}
Related
In Javadoc, I can see Class ClassCastException's Constructor with String parameter. But ClassCastException's Instance automatically is created (by JVM), I don't know how to use ClassCastException's Constructor.
In my code, I want to get a result "wrong", not "B cannot be cast to C".
class Prac {
public static void main(String[] args) {
try {
ClassCastException e = new ClassCastException("wrong");
A a = new B();
C c = (C)a;
}
catch(ClassCastException e) {
System.out.println(e.getMessage());
}
}
}
class A {
}
class B extends A {
}
class C extends A{
}
Result : B cannot be cast to C
If you want the result "wrong", then just print "wrong".
public static void main(String[] args) {
try {
A a = new B();
C c = (C)a;
}
catch(ClassCastException e) {
System.out.println("wrong");
}
}
No need to go tinkering around with the exception.
I am trying to re-build an OOP approach to mobile verification at the developers discretion. The concept I come up with is to allow for interfaces to manipulate the class. If the class implements the interface, then the verify method will be executed.
The problem I am facing, because I am only used to programming in less strongly-typed languages (PHP) is how to get a protected variable from a class extending the current class.
_areaCodes.stream().forEach(o -> {
try {
int prefix = Integer.parseInt(this._mobileNumber.charAt(0), this._mobileNumber.charAt(1));
} catch (Exception e) {}
});
This line of code is now giving me an error
_mobileNumber cannot be resolved or is not a field
Here is my full code and here is an example I wrote of the same concept in PHP which I am trying to implement in Java.
import java.util.ArrayList;
interface Verification
{
public void initVerification();
}
class AreaCode
{
private int _code;
private String _country;
public AreaCode(int code, String country)
{
this._code = code;
this._country = country;
}
public int getAreaCode() { return this._code; }
public String getAreaCountry() { return this._country; }
}
class VerificationHandler
{
private ArrayList<AreaCode> _areaCodes = new ArrayList<AreaCode>() {{
this.add(new AreaCode(44, "UNITED KINGDOM"));
this.add(new AreaCode(91, "INDIA"));
}};
public void initVerification()
{
if(this instanceof Verification) {
this.verify();
}
}
protected void verify()
{
_areaCodes.stream().forEach(o -> {
try {
int prefix = Integer.parseInt(this._mobileNumber.charAt(0), this._mobileNumber.charAt(1));
} catch (Exception e) {}
});
}
}
class Main extends VerificationHandler implements Verification {
protected String _mobileNumber = "+447435217761";
}
public class Hack1337 { public static void main(String[] args) { new Main(); } }
How can I retrieve a variable in a class extending another, ie:
class A { public String getB() { return this.b; } }
class B extends A { protected String b = 'A should get this'; }
B b = new B().getB();
Only instances of class B, or sub-classes of B can access the b instance variable directly (unless you cast A to B within the body of the A class, which is bad practice).
You can give class A read-only access to that value by overriding getB():
class B extends A
{
protected String b = 'A should get this';
#Override
public String getB() {
return this.b;
}
}
and you may also want to make the getB() method abstract in class A (which means making class A abstract):
abstract class A
{
public abstract String getB();
}
This would only make sense if different sub-classes of A are expected to return different things in getB(). Otherwise, you may as well move the b variable to the base class A.
I have two classes A and B and they both have a common field in them, and I want to create a function in which if I pass Class A object then I want to set that common field value to the passed value and if I pass Class B object then I want to set that common field value to the passed value. Can anyone please tell me how can I do this, I am new to Java Generic Classes.
Otherwise I would have to make two different functions OR I would have to make an if and else which would decide that passed object belongs to which class ??
Class A
public class A{
int footer;
public void setFooter(int fo) {
footer = fo;
}
}
Class B
public class B{
int footer;
public void setFooter(int fo) {
footer = fo;
}
}
Class D
public class D{
public void change_footer(T generic_param, int value) {
generic_param.setFooter(value);
}
}
Class HelloWorld
public class HelloWorld{
public static void main(String []args){
Here I want to call
A a = new A();
new D().change_footer(a, 5);
B b = new B();
new D().change_footer(b, 5)
}
}
Thank You
And if I got all of the question wrong, and nor A nor B are generic, AND the type of field is fixed.
then you mean something like:
class D {
/*public <T extends Super> would be muuuch nicer here as well!*/
public /*static*/ <T> void change_footer(T obj, int data) {
//otherwise, you could just cast to Super...and set dat field.
if (obj instanceof A) {
((A) obj).setField(data);
} else if (obj instanceof B) {
((B) obj).setField(data);
} // else ... ?
}
}
Original answer:
Easy peasy (the "straight forward" implementation produces the desired results.):
class A<T> {
T daField;
public void setField(T pField) {
daField = pField;
}
public T getField() {
return daField;
}
}
class B<T> extends A {//empty
}
class Test {
public static void main(String... args) {
B<Object> testB1 = new B<>(); //
testB1.setField(new Object());
System.out.println(testB1.getField());
B<String> testB2 = new B<>();
testB2.setField("blah blah");
System.out.println(testB2.getField());
B<Integer> testB3 = new B<>();
testB3.setField(42);
System.out.println(testB3.getField());
}
}
System.out:
java.lang.Object#6d06d69c
blah blah
42
It get's (little) more complicated, when you want to instantiate Ts ...but still possible/other question. :)
Edit to your comment:
If there's only one common field, then why not:
/*abstract */class Super<T> {
T daField;
public void setField(T pField) {
daField = pField;
}
public T getField() {
return daField;
}
}
? ...and:
class A<T> extends Super { ... }
class B<T> extends Super { ... }
I have the sama java object TestData in to packages (A & B). I have made a function that processes the object for a standard business functionality.
CommonFunc.java:
import A.TestData ;
class CommonFunc
{
/// .....
public static TestData processTestData(Date d1, String s1){
TestData testData = new TestData ();
/// set some testData porperties based on d1 and s1
/// e.g : testData.setInitialDate(d1);
return testData ;
}
}
The problem here is that the compiler has to load the object from one of the packages lets say package (A), so when I expect the data to be returned to a local variable from package (B) I get incompatible type error :
File using B TestData and needs to call the function processTestData:
import B.TestData;
// ...
TestData obj = CommonFunc.processTestData(new Date(), "test");
// ...
Is there a way to overcome this problem keeping a common function for both?
Is there a way to overcome this problem keeping a common function for both?
No and yes. On the general case, you cannot.
But you can, IFF you can make the two classes adopt the same interface, with the common methods declared in the same interface. See below, with apologies for the change in the class names:
interface C {
public Date getA();
public void setA(Date a);
}
interface C_Factory <X extends C> {
X createInstance();
}
class C1 implements C {
Date a;
int b;
public C1() {
super();
}
public Date getA() { return a; }
public void setA(Date a) { this.a = a; }
public int getB() { return b; }
public void setB(int b) { this.b = b; }
}
class C2 implements C {
Date a;
float b;
public C2() {
super();
}
public Date getA() { return a; }
public void setA(Date a) { this.a = a; }
public float getB() { return b; }
public void setB(float b) { this.b = b; }
}
public class CommonFunc {
// You need this extra param to create instances----
// V
static <X extends C> X doSomething(Date d, Class<X> clazz)
throws InstantiationException, IllegalAccessException
// You'll have to accept those exceptions as well
{
// the next statement uses clazz as a factory for new X instances
// As such, you can abstract the method further and use
// a custom Factory class instead.
X toret=clazz.newInstance();
toret.setA(d);
// something else
return toret;
}
// A custom factory variant of the above
static <X extends C> X doSomething(Date d, C_Factory<X> factory)
{
X toret=factory.createInstance();
toret.setA(d);
// something else
return toret;
}
static public void main(String[] args) {
try {
C1 c1=doSomething(new Date(), C1.class);
C2 c2=doSomething(new Date(), C2.class);
} catch (InstantiationException | IllegalAccessException e) {
// Should not happen
e.printStackTrace();
}
}
}
I do not see how it is possible in the above example you have posted, The best way out is to make the TestData an interface and have implementations in 2 packages. Then, to decide whether to return A TestDataImpl or B TestDataImpl, take another parameter in the processData, for simplicity, let us say a boolean. Based on true or false instantiate A TestDataImpl or B TestDataImpl and return the same. Where the return type of processData is the interface type
This is probably would be the most straightforward way of reusing the processData method.
Is there a way to implement something like
List<Class<? implements MyInterface>> ClassList = new ArrayList<Class<? implements MyInterface>>();
my goal is to create a hashmap from that list, where the keys are the toString methods of the class (defined in MyInterface) and the values are the classes itself. The toString method of every object of this class returns the same result. This way I could create Instances of the classes using the map by searching the right strings.
thank you for trying to help,
greetings
List<Class<? implements MyInterface>> ClassList = new ArrayList<Class<? implements MyInterface>>();
should be
List<Class<? extends MyInterface>> ClassList = new ArrayList<Class<? extends MyInterface>>();
there is no implements keyword in the world of generics. if you want a type parameter that implements an interface , use the extends keyword to represent it.
Since you seem interested by the way I explained, here is a quick implementation, to verify it can be done...
import java.util.ArrayList;
import java.util.List;
enum NumberClass
{
ONE("One"),
TWO("Two"),
THREE("Three");
private final String className;
NumberClass(String name)
{
className = name;
}
String getName()
{
return className;
}
}
public class Test
{
public static void main(String[] args)
{
List<NumberClass> numbers = new ArrayList<NumberClass>();
numbers.add(NumberClass.ONE);
numbers.add(NumberClass.THREE);
numbers.add(NumberClass.TWO);
numbers.add(NumberClass.ONE);
numbers.add(NumberClass.THREE);
numbers.add(NumberClass.ONE);
numbers.add(NumberClass.TWO);
SomeNumber[] nbs = new SomeNumber[numbers.size()];
int i = 0;
for (NumberClass nbC : numbers)
{
SomeNumber nb;
try
{
nb = (SomeNumber) Class.forName(nbC.getName()).newInstance ();
nbs[i++] = nb;
}
// Cleanly handle them!
catch (InstantiationException e) { System.out.println(e); }
catch (IllegalAccessException e) { System.out.println(e); }
catch (ClassNotFoundException e) { System.out.println(e); }
}
for (SomeNumber sn : nbs)
{
System.out.println(sn.getClass().getName() + " " + sn.getValue());
}
}
}
// The following must be in their own files, of course
public interface SomeNumber
{
int getValue();
}
public class One implements SomeNumber
{
public int getValue() { return 1; }
}
public class Two implements SomeNumber
{
public int getValue() { return 2; }
}
public class Three implements SomeNumber
{
public int getValue() { return 3; }
}
If it doesn't answer your question, consider it as educational material, I hope. :-)