2

I use an API which has this method:

public void doSomething(List<Object> list); 

On our application side we have only one certain class say 'MyClass' that should be passed to this api method.

So for this restriction I created a method which will call the API:

public void myMethod(List<MyClass>list){ api.doSomething(list); } 

Of course it doesnt compile and I cant use wild cards because I cant touch the api code. Right now I am casting the MyClass generic to Object by hand.

Is there a better solution for this?

2
  • You can cast it to List: api.doSomething((List) list);. Commented Jul 19, 2019 at 8:18
  • Not sure if it will work, you can either have myMethod(List<?> list) or myMethod(List list). They will probably receive a warning but not an error, at least the second one. Commented Jul 19, 2019 at 8:22

3 Answers 3

2

No, the API definition is "wrong" (if you want to avoid casting). A best API definition could be:

// *external* API static class API { public void doSomething(List<? extends Object> list) { throw new IllegalStateException("not implemented"); } } 

Now, you can call with any ? extending Object:

List<String> xs = new ArrayList<>(); new API().doSomething(xs); 

As a side note, any object extend Object then ? extends Object is redundant. This API could be rewritten as:

public void doSomething(List<?> list) 

But in general, you will have something like:

public void doSomething(List<ApiDataModel> list) 

Then, the proper way is again:

public void doSomething(List<? extends ApiDataModel> list) 
Sign up to request clarification or add additional context in comments.

4 Comments

Well, you could replace <? extends Object> with simply <?>, because they are synonymous.
Yes but to understand it I think is better my explicit version.
@josejuan <?> is more idiomatic.
Of course @AndyTurner, but I want reforce the extend idea (i'll update to clarify)
1

How about just doing something simple like;

public static void myMethod(List<MyClass> list) { doSomething(new ArrayList<>(list)); } 

Unless you are removing or adding things to the list, you can use this. Otherwise since you will be instantiating a new list, any changes to it will be lost and not reflected to your list, but changes on the individual elements of MyClass objects will be.

Comments

1

You can create a List from List in this way:

public void myMethod(List<MyClass> list){ List<Object> objectList = new ArrayList<>(); objectList.addAll(list) api.doSomething(objectList); } 

Or simply use a non-generic cast (this will generate a warning):

public void myMethod(List<MyClass> list){ api.doSomething((List)list); } 

1 Comment

"Or simply use a non-generic cast (this will generate a warning):" You should point out the danger that the warning is highlighting: that doSomething is allowed to add instances of any subclass of Object to the parameter list, which could then break the type safety of other things using list.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.