I am new to java programming and I am learning generics.I tried to do some generics program by myself and I am getting Exception in thread "main" java.lang.ClassCastException: [Ljava.lang.Object; cannot be cast to [Lcom.ashwin.model.Car;.
I have a Vehicle Class:
public class Vehicle {
private int id;
private String name;
private String color;
private int plateNo;
//omitted getters and setters
}
I have a Car class extending Vehicle Class.
public class Car extends Vehicle {
public Car(int id, String name, String color, int plateNo) {
super.setId(id);
super.setColor(color);
super.setPlateNo(plateNo);
}
}
I have CarDAOImpl.java class:
public class CarDAOImpl implements VehicleDAO<Car> {
private static ParkingLot<Car> park=new ParkingLot<Car>(10);
#Override
public boolean insert(Car v) {
if(park.getSpace()==-1) {
return false;
}
else {
park.setSpace(park.getSpace()-1);
park.setVehicle(v);
return true;
}
}
#Override
public boolean delete(Car k) {
if(park.getSpace()==10) {
return false;
}
else {
boolean result=park.deleteVehicle(k);
return result;
}
}
#Override
public Car[] getAll() {
return park.getVehicle();
}
}
I have another ParkingLot.java class:
public class ParkingLot<T> {
private int space;
private T[] vehicle;
public ParkingLot() {
}
public ParkingLot(int sp) {
this.vehicle=(T[])new Object[sp];
this.space=sp;
}
public int getSpace() {
return space;
}
public void setSpace(int space) {
this.space = space;
}
public T[] getVehicle() {
return vehicle;
}
public void setVehicle(T vehicle) {
this.vehicle[space]=vehicle;
}
public <T extends Vehicle> boolean deleteVehicle(T v) {
for(int i=0;i<vehicle.length;i++) {
if(((Vehicle) vehicle[i]).getId()==v.getId()) {
vehicle[i]=null;
return true;
}
}
return false;
}
}
My main method is:
public class Main {
public static void main(String[] args) {
VehicleDAO<Car> v=new CarDAOImpl();
boolean inserted=v.insert(new Car(1,"ford","Red",1234));
System.out.println(inserted);
Car[] c=v.getAll();
for(int i=0;i<c.length;i++)
{
System.out.println(c[i]);
}
}
}
I am getting error at this line of CarDAOImpl.java class:
#Override
public Car[] getAll() {
return park.getVehicle();
}
The exception is:
Exception in thread "main" java.lang.ClassCastException: [Ljava.lang.Object; cannot be cast to [Lcom.ashwin.model.Car;
You need to update your constructor to include the class object as a parameter:
public ParkingLot(Class<T> clazz, int sp) {
this.vehicle= (T[]) Array.newInstance(clazz, sp);
this.space=sp;
}
And your variable declaration should look like this:
private static ParkingLot<Car> park = new ParkingLot<>(Car.class, 10);
Related
I would appreciate any help in solving the following question.
Design and implement a subclass of GenericOrder called ComputerPartyOrder that takes an arbitrary number of different classes of ComputerPart objects, Peripheral objects, Cheese objects, Fruit objects and Service objects.
here is the code for Product class and GerericOrder class.
abstract class Product {
protected float price;
// return the price of a particular product
abstract float price();
//public getType() {
//
//}
}
//------------------------------------------------------------
class ComputerPart extends Product {
public ComputerPart(float p) {
price = p;
}
public float price() { return price; }
}
class Motherboard extends ComputerPart {
protected String manufacturer;
public Motherboard(String mfg, float p) {
super(p);
manufacturer = mfg;
}
public String getManufacturer() { return manufacturer; }
}
class RAM extends ComputerPart {
protected int size;
protected String manufacturer;
public RAM(String mfg, int size, float p) {
super(p);
this.manufacturer = mfg;
this.size = size;
}
public String getManufacturer() { return manufacturer; }
}
class Drive extends ComputerPart {
protected String type;
protected int speed;
public Drive(String type, int speed, float p) {
super(p);
this.type = type;
this.speed = speed;
}
public String getType() { return type; }
public int getSpeed() { return speed; }
}
class Peripheral extends Product {
public Peripheral(float p) {
price = p;
}
public float price() { return price; }
}
class Printer extends Peripheral {
protected String model;
public Printer(String model, float p) {
super(p);
this.model = model;
}
public String getModel() { return model; }
}
class Monitor extends Peripheral {
protected String model;
public Monitor(String model, float p) {
super(p);
this.model = model;
}
public String getModel() { return model; }
}
class Service extends Product {
public Service(float p) {
price = p;
}
public float price() { return price; }
}
class AssemblyService extends Service {
String provider;
public AssemblyService(String pv, float p) {
super(p);
provider = pv;
}
public String getProvider() { return provider; }
}
class DeliveryService extends Service {
String courier;
public DeliveryService(String c, float p) {
super(p);
courier = c;
}
public String getCourier() { return courier; }
}
//-------------------------------------------------------
class Cheese extends Product {
public Cheese(float p) {
price = p;
}
public float price() { return price; }
}
class Cheddar extends Cheese {
public Cheddar(float p) {
super(p);
}
}
class Mozzarella extends Cheese {
public Mozzarella(float p) {
super(p);
}
}
class Fruit extends Product {
public Fruit(float p) {
price = p;
}
public float price() { return price; }
}
class Apple extends Fruit {
public Apple(float p) {
super(p);
}
}
class Orange extends Fruit {
public Orange(float p) {
super(p);
}
}
GenericOrder:
import java.util.ArrayList;
import java.util.List;
public abstract class GenericOrder<T> extends Product {
private static long counter = 1;
private final long id = counter++;
private List<T> Item;
public GenericOrder() {
Item = new ArrayList<T>();
}
public long getid() {
return id;
}
public void addItem(T newItem) {
Item.add(newItem);
}
public List<T> getItem() {
return Item;
}
public void setItem(List<T> Item) {
this.Item = Item;
}
}
EDIT: Code so far
public abstract class ComputerPartyOrder extends GenericOrder {
GenericOrder GOrder = new GenericOrder() {
#Override
float price() {
return 0;
}
};
public void input(Product newitem) {
GOrder.addItem(newitem);
}
public void output() {
System.out.println(GOrder.getItem());
}
}
You have the right idea, but GenericOrder does not need a type parameter T. Instead, you can set the type of Item to Product (the superclass of all the different types of products).
public abstract class GenericOrder extends Product {
private static long counter = 1;
private final long id = counter++;
private List<Product> Item;
public GenericOrder() {
Item = new ArrayList<Product>();
}
public long getid() {
return id;
}
public void addItem(Product newItem) {
Item.add(newItem);
}
public List<Product> getItem() {
return Item;
}
public void setItem(List<Product> Item) {
this.Item = Item;
}
}
You will still be able to call addItem with any instance of a subclass of Product.
I would also suggest renaming Item to item, uppercase names are usually used for types, not variables.
Consider the below example, what is a good way to avoid the warning with respect to unchecked conversion below?
Usercase is as
An interface which represent a generic statemachine
Each statemachine implementation requires a service, a set of utils required while running corresponding statemachines.
A default service which provides common services across statemachines
A transaction(txn) a binder of state and service.
import java.util.function.Consumer;
public class GenericsTest {
public static void main(String[] args) {
AService service = new AService("Aservice");
new Txn<>(service).next();
new Txn<>(new DefaultState()).next();
}
}
// ----------------------------------------------------------- //
interface Service {
String getName();
<T extends Service> State<T> getState();// this is unclear how to use generics here
}
interface State<T extends Service> {
Consumer<Txn<T>> getFunction();
int getN();
}
// ----------------------------------------------------------- //
class Txn<T extends Service> {
private T service;
private State<T> current;
Txn(State<T> current) {
this.current = current;
}
Txn(T service) {
this.service = service;
this.current = this.service.getState();
}
int next() {
do {
current.getFunction().accept(this);
} while (current.getN()>0);
return current.getN();
}
public State<T> getCurrent() {
return current;
}
public void setCurrent(State<T> current) {
this.current = current;
}
}
// ----------------------------------------------------------- //
abstract class DefaultService implements Service {
private String name;
public DefaultService(String name) {
this.name = name;
}
public String getName(){
return this.name.toUpperCase();
}
}
class AService extends DefaultService implements Service {
public AService(String name) {
super(name);
}
#Override
public State<AService> getState() {
return new AState(6);
}
}
// ----------------------------------------------------------- //
class DefaultState implements State<DefaultService> {
#Override
public Consumer<Txn<DefaultService>> getFunction() {
return (txn) -> System.out.println("hurray now left is to do default at "+txn.getCurrent().getN());
}
#Override
public int getN() {
return 0;
}
}
class AState implements State<AService> {
private int n;
AState(int n) {
this.n = n;
}
#Override
public int getN() {
return n;
}
#Override
public Consumer<Txn<AService>> getFunction() {
return (txn) -> {
int n = txn.getCurrent().getN();
System.out.println(n);
txn.setCurrent(new AState(--n));
};
}
}
Basically Please program to the interfaces (4 changes listed below):
DefaultService already implements Service
State<AService> change to State<Service>
class AState implements State<Service>
program to the interfaces: class Txn<T extends Service> {
Corrected code below:
import java.util.function.Consumer;
public class GenericsTest {
AService service = new AService("Aservice");
new Txn<>(service).next();
new Txn<>(new DefaultState()).next();
}
}
// ----------------------------------------------------------- //
interface Service {
String getName();
<T extends Service> State<T> getState();// this is unclear how to use generics here
}
interface State<T extends Service> {
Consumer<Txn<T>> getFunction();
int getN();
}
// ----------------------------------------------------------- //
class Txn<T extends Service> {
private T service;
private State<T> current;
Txn(State<T> current) {
this.current = current;
}
Txn(T service) {
this.service = service;
this.current = this.service.getState();
}
int next() {
do {
current.getFunction().accept(this);
} while (current.getN()>0);
return current.getN();
}
public State<T> getCurrent() {
return current;
}
public void setCurrent(State<T> current) {
this.current = current;
}
}
// ----------------------------------------------------------- //
abstract class DefaultService implements Service {
private String name;
public DefaultService(String name) {
this.name = name;
}
public String getName(){
return this.name.toUpperCase();
}
}
class AService extends DefaultService {
public AService(String name) {
super(name);
}
#Override
public State<Service> getState() {
return new AState(6);
}
}
// ----------------------------------------------------------- //
class DefaultState implements State<DefaultService> {
#Override
public Consumer<Txn<DefaultService>> getFunction() {
return (txn) -> System.out.println("hurray now left is to do default at "+txn.getCurrent().getN());
}
#Override
public int getN() {
return 0;
}
}
class AState implements State<Service> {
private int n;
AState(int n) {
this.n = n;
}
#Override
public int getN() {
return n;
}
#Override
public Consumer<Txn<Service>> getFunction() {
return (txn) -> {
int n = txn.getCurrent().getN();
System.out.println(n);
txn.setCurrent(new AState(--n));
};
}
}
I'm trying to store a coordnates (array of double) using Realm-java,but I'm not able to do it.
Here is an example of json that I'm trying to parse:
{"_id":"597cd98b3af0b6315576d717",
"comarca":"string",
"font":null,
"imatge":"string",
"location":{
"coordinates":[41.64642,1.1393],
"type":"Point"
},
"marca":"string",
"municipi":"string",
"publisher":"string",
"recursurl":"string",
"tematica":"string",
"titol":"string"
}
My global object code is like that
public class Images extends RealmObject implements Serializable {
#PrimaryKey
private String _id;
private String recursurl;
private String titol;
private String municipi;
private String comarca;
private String marca;
private String imatge;
#Nullable
private Location location;
private String tematica;
private String font;
private String parentRoute;
public Location getLocation() {return location;}
public void setLocation(Location location) {this.location = location;}
public String getParentRoute() {
return parentRoute;
}
public void setParentRoute(String parentRoute) {
this.parentRoute = parentRoute;
}
public String get_id() {
return _id;
}
public void set_id(String _id) {
this._id = _id;
}
public String getFont() {
return font;
}
public void setFont(String font) {
this.font = font;
}
public String getRecursurl() {
return recursurl;
}
public void setRecursurl(String recursurl) {
this.recursurl = recursurl;
}
public String getTitol() {
return titol;
}
public void setTitol(String titol) {
this.titol = titol;
}
public String getMunicipi() {
return municipi;
}
public void setMunicipi(String municipi) {
this.municipi = municipi;
}
public String getComarca() {
return comarca;
}
public void setComarca(String comarca) {
this.comarca = comarca;
}
public String getMarca() {
return marca;
}
public void setMarca(String marca) {
this.marca = marca;
}
public String getImatge() {
return imatge;
}
public void setImatge(String imatge) {
this.imatge = imatge;
}
public String getTematica() {
return tematica;
}
public void setTematica(String tematica) {
this.tematica = tematica;
}
And Location is a composite of type and a realmlist
Location.java
public class Location extends RealmObject implements Serializable {
private String type;
private RealmList<RealmDoubleObject> coordinates;
public Location() {
}
public String getType() {
return type;
}
public void setType(String type) {
this.type = type;
}
public RealmList<RealmDoubleObject> getCoordinates() {
return coordinates;
}
public void setCoordinates(RealmList<RealmDoubleObject> coordinates) {
this.coordinates = coordinates;
}
}
RealmDoubleObject.java
public class RealmDoubleObject extends RealmObject implements Serializable{
private Double value;
public RealmDoubleObject() {
}
public Double getDoublevalue() {
return value;
}
public void setDoublevalue(Double value) {
this.value = value;
}
}
The error is com.google.gson.JsonSyntaxException: java.lang.IllegalStateException: Expected BEGIN_OBJECT but was NUMBER at path $[0].location.coordinates[0] but I'm not able to figure out why this number is not "fitting" by RealmDoubleObject.
For those that not familiar with realm RealmList doesn't work and you have to build your own realm object.
Thank you. I hope to find some Realm experts here!
SOLVED:
using Gson deserializer it can be done
First we have to initialize the gson object like this
Gson gson = new GsonBuilder()
.setExclusionStrategies(new ExclusionStrategy() {
#Override
public boolean shouldSkipField(FieldAttributes f) {
return f.getDeclaringClass().equals(RealmObject.class);
}
#Override
public boolean shouldSkipClass(Class<?> clazz) {
return false;
}
})
.registerTypeAdapter(new TypeToken<RealmList<RealmDoubleObject>>() {}.getType(), new TypeAdapter<RealmList<RealmDoubleObject>>() {
#Override
public void write(JsonWriter out, RealmList<RealmDoubleObject> value) throws IOException {
// Ignore
}
#Override
public RealmList<RealmDoubleObject> read(JsonReader in) throws IOException {
RealmList<RealmDoubleObject> list = new RealmList<RealmDoubleObject>();
in.beginArray();
while (in.hasNext()) {
Double valor = in.nextDouble();
list.add(new RealmDoubleObject(valor));
}
in.endArray();
return list;
}
})
.create();
And then we have to put some other constructor method
public RealmDoubleObject(double v) {
this.value = v;
}
and this is all.
Thanks for the help #EpicPandaForce
I'm trying to obfuscate a parcelable class with Proguard:
Before adding the Parcelable part the class is:
public class Foo{
private String value;
public String getValue() {
return value;
}
public void setValue(String value) {
this.value = value;
}
}
The obfuscated result is:
public class a
{
private String a;
public String a()
{
return this.a;
}
public void a(String paramString)
{
this.a = paramString;
}
}
After adding implementing parcelable the example class is
public class Foo implements Parcelable {
private String value;
private Foo(Parcel in) {
value = in.readString();
}
public Foo() {
}
public String getValue() {
return value;
}
public void setValue(String value) {
this.value = value;
}
#Override
public int describeContents() {
return 0;
}
#Override
public void writeToParcel(Parcel dest, int flags) {
dest.writeString(value);
}
public static final Parcelable.Creator<Foo> CREATOR
= new Parcelable.Creator<Foo>() {
public Foo createFromParcel(Parcel in) {
return new Foo(in);
}
public Foo[] newArray(int size) {
return new Foo[size];
}
};
}
The obfuscated result is
public class Foo implements Parcelable {
public static final Parcelable.Creator CREATOR = new a();
private String a;
public Foo() {
}
private Foo(Parcel paramParcel) {
this.a = paramParcel.readString();
}
public String a() {
return this.a;
}
public void a(String paramString) {
this.a = paramString;
}
public int describeContents() {
return 0;
}
public void writeToParcel(Parcel paramParcel, int paramInt) {
paramParcel.writeString(this.a);
}
}
class a implements Parcelable.Creator {
public Foo a(Parcel paramParcel) {
return new Foo(paramParcel, null);
}
public Foo[] a(int paramInt) {
return new Foo[paramInt];
}
}
How can I configure proguard for obfuscate the whole class (including name, params and methods) except the parcelable part?
Thanks
Try putting this in your proguard.cfg file:
-keepclassmembers class * implements android.os.Parcelable {
public static final android.os.Parcelable$Creator *;
}
That should preserve Parcelable part and obfuscate everything else.
I have a class that extends DataRow:
import org.jdesktop.dataset.DataRow;
public class MainDataRow extends DataRow {
private MainDataTable baseDataTable;
protected MainDataRow(MainDataTable dt) {
super(dt);
this.baseDataTable = dt;
}
public int getId() { return (int) super.getValue(baseDataTable.getColId()); };
public void setId(int id) { super.setValue(baseDataTable.getColId(), id); };
public int getDelta() { return (int) super.getValue(baseDataTable.getColDelta()); };
public void setDelta(int delta) { super.setValue(baseDataTable.getColDelta(), delta); };
public String getNombre() { return (String) super.getValue(baseDataTable.getColNombre()); };
public void setNombre(String nombre) { super.setValue(baseDataTable.getColNombre(), nombre); };
Also MainDataTable extends DataTable, and returns valid columns for getColId(), getColDelta(), getColNombre().
I would like to do:
MainDataTable dt = new MainDataTable(ds);
MainDataRow dr = (MainDataRow) dt.appendRow();
But this is not possible due to a CastClassException (dt.appendRow return DataRow and MainDataRow is extending DataRow, not vice versa, so the only possibility could be something similar to DataRow dr = (DataRow) new MainDataRow(dt);).
In c++ it can be easyly achieved through DataRowBuilder, overriding NewRowFromBuilder() in MainDataTable and overriding the protected creator from DataRowBuilder in MainDataRow (Casting DataRow to Strongly-Typed DataRow: How do they do it?).
How could I do it in Java?
Edit
MainDataTable class:
public class MainDataTable extends TypedDataTable<MainDataRow> {
...
}
And TypedDataTable class:
public abstract class TypedDataTable<TypeOfRow> extends DataTable {
protected boolean locked;
public TypedDataTable(DataSet ds, boolean appendRowSupported) {
super(ds);
InitClass();
super.setAppendRowSupported(appendRowSupported);
locked = false;
}
public Object clone() {
try {
return super.clone();
} catch (CloneNotSupportedException e) {
e.printStackTrace();
return null;
}
}
#Override
public abstract DataRow appendRow();
#Override
public abstract DataRow appendRowNoEvent();
public abstract void InitVars();
public abstract void InitClass();
public boolean isLocked() {
return locked;
}
public void setLocked(boolean locked) {
this.locked = locked;
}
}
Override appendRow() and appendRowNoEvent() in MainDataTable to return a MainDataRow
public abstract class TypedDataTable<TypeOfRow extends DataRow> extends DataTable {
protected boolean locked;
public TypedDataTable(DataSet ds, boolean appendRowSupported) {
super(ds);
InitClass();
super.setAppendRowSupported(appendRowSupported);
locked = false;
}
public Object clone() {
try {
return super.clone();
} catch (CloneNotSupportedException e) {
e.printStackTrace();
return null;
}
}
#Override
public TypeOfRow appendRowNoEvent() {
if (appendRowSupported) {
TypeOfRow row = createDataRow(); //<-- HERE we create a MainDataRow!!!
rows.add(row);
return row;
} else {
return null;
}
}
#Override
public TypeOfRow appendRow() {
return (TypeOfRow)super.appendRow();
}
public abstract TypeOfRow createDataRow();
public abstract void InitVars();
public abstract void InitClass();
public boolean isLocked() {
return locked;
}
public void setLocked(boolean locked) {
this.locked = locked;
}
}