开发者

How to initialize an object with a list of different types?

Hey, I'm initializing a ListRepository with two different types of initialization lists. The best way would be something like this.

public ListRepository(String id, List<PrimaryKey> initilizationList)
{
   // Load objects from data source via primary key.
}

public ListRepository(String id, List<DomainObject> initilizationList)
{
   // Store objects directly
}

Unfortunately this is not possible due to runtime开发者_如何学Python type erasure. I don't like a constructor approach with List<?> as an argument, this leads to an ugly instanceof check of the first entry, to determine the list type and handle it.

How do you solve such a problem with an intuitive and clean API?


The constructor is doing far more than initialising the object. It is best to keep constructors simple.

I would use a static method to perform each query.

public static ListRepository<PrimaryKey> loadFromPrimaryKey(String id, List<PrimaryKey> initilizationList) {
   // Load objects from data source via primary key.
}

public static ListRepository<PrimaryKey> loadFromDomainObject(String id, List<DomainObject> initilizationList) {
   // Store objects directly
}

You would have one constructor which just takes the resulting data. This would make it much clearer as to what the methods will build.


Use factory method

class ListRepository {     
    public static ListRepository createPrimaryKeysRepository(String id, List<PrimaryKey> initilizationList){}
    public static ListRepository createDomainObjectsRepository(String id, List<DomainObject> initilizationList){}
}


Use factory methods; e.g.

private ListRepository(String id) {
   this.id = id;
}

public static ListRepository createFromPrimaryKeys(String id, List<PrimaryKey> init) {
   ListRepository res = new ListRepository(id);
   // Load objects from data source via primary key.
   return res;
}

public static ListRepository createFromObjects(String id, List<DomainObject> init) {
   ListRepository res = new ListRepository(id);
   // Store objects directly
   return res;
}


You could wrap the lists in an object containing the list:

public ListRepository(String id, PrimaryKeyList initilizationList)
{
   // Load objects from data source via primary key.
}

public ListRepository(String id, DomainObjectList initilizationList)
{
   // Store objects directly
}

or you could use only one method, and pass an extra argument, being a boolean or an enum:

public ListRepository(String id, List<?> initilizationList initilizationList, boolean isPrimaryKey)
{
   // Load objects from data source
}


How about

    
public ListRepository(String id, PrimaryKey...keys) {
   // Load objects from data source via primary key.
}

public ListRepository(String id, DomainObject...stuff)
{
   // Store objects directly
}

or, use specialized ListRepositoryInitializers


public ListRepository(String id, List<PrimaryKey> listByKey , List<DomainObject> listByObject)
{
  if(listByKey == null)
   // Load objects from data source via primary key.
  else
    // Store Objects Directly
}

Instead of writing the Method or Constructor Overloading, you can achieve the same by using Method which accepts both parameters and take any of them.

Hope this will solves your problem.


This might be a bit ugly but what about:

public ListRepository(String id, PrimaryKey[] initilizationList) {
  [...]
}

public ListRepository(String id, DomainObject[] initilizationList) {
  [...]
}

Udo.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜