What's this generics usage in Java? X.<Y>method()

蓝咒 提交于 2020-01-22 10:37:08

问题


I've read the whole SCJP6 book Sierra and Bates book, scored 88% the exam.

But still, i never heard of how this kind of code works as it's not explained in the generics chapter:

Collections.<TimeUnit>reverseOrder()

What is this kind of generics usage? I discovered it in some code but never read anything about it. It seems to me it permits to give some help to type inference. I've tried to search about that but it's not so easy to find (and it's not even in the SCJP book/exam!)

So can someone give me a proper explaination of how it works, which are all the usecases etc?

Thanks


Edit Thanks for the answers but i expected more details :) so if someone want to add some extra informations:

What about more complex cases like

  • Using a type declared in class , can i do something like Collections.<T>reverseOrder() for exemple?
  • Using extends, super?
  • Using ?
  • Giving the compiler only partial help (ie O.manyTypesMethod<?,MyHelpTypeNotInfered,?,?,?,?,?>() )

回答1:


It is explicit type specification of a generic method. You can always do it, but in most cases it's not needed. However, it is required in some cases if the compiler is unable to infer generic type on its own.

See an example towards the end of the tutorial page.

Update: only the first of your examples is valid. The explicit type argument must be, well, explicit, so no wildcards, extends or super is allowed there. Moreover, either you specify each type argument explicitly or none of them; i.e. the number of explicit type arguments must match the number of type parameters of the called method. A type parameter such as T is allowed if it is well defined in the current scope, e.g. as a type parameter of the enclosing class.




回答2:


You are 100% correct, it is to help with type inference. Most of the time you don't need to do this in Java, as it can infer the type (even from the left hand side of an assignment, which is quite cool). This syntax is covered in the generics tutorial on the Java website.




回答3:


Just a small addition to the other responses.

When getting the according compiler error:

While the "traditional" casting approach

(Comparator<TimeUnit>) Collections.reverseOrder()

looks similar to the generics approach

Collections.<TimeUnit>reverseOrder()

the casting approach is of course not type-safe (possible runtime exception), while the generics approach would create a compilation error, if there is an issue. Thus the generics approach is preferred, of course.




回答4:


As the other answers have clarified, it's to help the compiler figure out what generic type you want. It's usually needed when using the Collections utility methods that return something of a generic type and do not receive parameters.

For example, consider the Collections.empty* methods, which return an empty collection. If you have a method that expects a Map<String, String>:

public static void foo(Map<String, String> map) { }

You cannot directly pass Collections.emptyMap() to it. The compiler will complain even if it knows that it expects a Map<String, String>:

// This won't compile.
foo(Collections.emptyMap());

You have to explicitly declare the type you want in the call, which i think looks quite ugly:

foo(Collections.<String, String>emptyMap());

Or you can omit that type declaration in the method call if you assign the emptyMap return value to a variable before passing it to the function, which i think is quite ridiculous, because it seems unnecessary and it shows that the compiler is really inconsistent: it sometimes does type inference on generic methods with no parameters, but sometimes it doesn't:

Map<String, String> map = Collections.emptyMap();
foo(map);

It may not seem like a very important thing, but when the generic types start getting more complex (e.g. Map<String, List<SomeOtherGenericType<Blah>>>) one kind of starts wishing that Java would have more intelligent type inference (but, as it doesn't, one will probably start writing new classes where it's not needed, just to avoid all those ugly <> =D).




回答5:


In this case it is a way of telling the reverseOrder method what kind of ordering should be imposed on the object, based on what type you specify. The comparator needs to get specific information about how to order things.



来源:https://stackoverflow.com/questions/10945616/whats-this-generics-usage-in-java-x-ymethod

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!