Java 如何修复 1.6 中低于 1.7 的源代码级别不允许使用“<>”运算符?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/23677597/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How to fix '<>' operator is not allowed for source level below 1.7 in 1.6?
提问by Nick
I have a Java 1.6 Android project. I have a third-party code that does not compile:
我有一个 Java 1.6 Android 项目。我有一个无法编译的第三方代码:
import org.springframework.http.HttpEntity;
//...
HttpHeaders requestHeaders = new HttpHeaders();
//...
new HttpEntity<>(requestHeaders);
It says: '<>' operator is not allowed for source level below 1.7
它说:低于 1.7 的源代码级别不允许使用“<>”运算符
I do not want to switch my project to 1.7. I have changed that line to
我不想将我的项目切换到 1.7。我已将该行更改为
new HttpEntity<Object>(requestHeaders);
and it compiles fine now.
它现在编译得很好。
But is my fix correct? What does Java 1.7 do with empty brackets?
但是我的修复正确吗?Java 1.7 用空括号做什么?
Update
更新
That new object is passed to function that accepts HttpEntity<?>
argument. I understand the idea of type inference, but I do not understand what does 1.7 compiler infer from the given code line.
该新对象被传递给接受HttpEntity<?>
参数的函数。我理解类型推断的想法,但我不明白 1.7 编译器从给定的代码行推断什么。
采纳答案by Shlublu
Your fix is almost correct and anyway not dangerous.
您的修复几乎是正确的,无论如何都不危险。
Object
is the root of the hierarchy and <> means "let the compiler infer the type", so any type that would have been inferred in 1.7 would be a specialization of Object
anyway.
Object
是层次结构的根,<> 表示“让编译器推断类型”,因此任何在 1.7 中推断的类型都将是Object
无论如何的特化。
After having seen your update: <?>
actually means "wildcard" (see here), so Object
is fine.
在看到你的更新后:<?>
实际上意味着“通配符” (见这里),所以Object
很好。
回答by Kayaman
You're missing the first part of the line there, I'm sure a HttpEntity wasn't created to just throw it away (check the type of the reference it's saved to).
您错过了该行的第一部分,我确定 HttpEntity 不是为了将其丢弃而创建的(检查它保存到的引用的类型)。
Java <1.7 requires this:
Java <1.7 要求:
SomeGenericClass<String> foo = new SomeGenericClass<String>();
SomeGenericClass<String> foo = new SomeGenericClass<String>();
Java 1.7 allows this as shorthand:
Java 1.7 允许将其作为速记:
SomeGenericClass<String> foo = new SomeGenericClass<>();
SomeGenericClass<String> foo = new SomeGenericClass<>();
回答by Avi
Your fix is correct. It would be better to use the exact (generic) type of `HttpEntitiy.
你的修复是正确的。最好使用`HttpEntitiy 的确切(通用)类型。
The idea behind the <>
operator is just to reduce verbosity in places where the compiler can infer the generic type from the code implicitly.
<>
运算符背后的想法只是减少编译器可以从代码中隐式推断泛型类型的地方的冗长。
As was described in this post
The Diamond Operator reduces some of Java's verbosity surrounding generics by having the compiler infer parameter types for constructors of generic classes
Diamond Operator 通过让编译器推断泛型类的构造函数的参数类型来减少 Java 围绕泛型的一些冗长
The need for such operator came from the verbosity of declaring new instances of generic types. In Java versions before 1.7 you had to define generics this way:
对此类运算符的需求来自于声明泛型类型的新实例的冗长性。在 1.7 之前的 Java 版本中,您必须以这种方式定义泛型:
List<MyClass> myClassCollection = new List<MyClass>();
Which is obviously redundant as the compiler can easily understand the type that should be in the construction of the object.
这显然是多余的,因为编译器可以很容易地理解构建对象时应该使用的类型。
Another great improvement that comes with this operator is the return of a generic type:
此运算符带来的另一个重大改进是返回泛型类型:
Before java 1.7:
在 Java 1.7 之前:
public List<MyClass> getMyClassCollection() {
if(some condition) {
return new ArrayList<MyClass>();
} else {
return LinkedList<MyClass>();
}
}
After java 1.7:
在 Java 1.7 之后:
public List<MyClass> getMyClassCollection() {
if(some condition) {
return new ArrayList<>();
} else {
return LinkedList<>();
}
}
This might seem trivial, but in fact there might be flows in which you can spare some such declarations. The huge advantage comes when you want to change your code. If you now change the method to return List<MyClassChild>
(where MyClassChild
extends MyClass
) you only need to change one placeand not several places.
这可能看起来微不足道,但实际上可能存在一些流程,您可以在其中省去一些此类声明。当您想要更改代码时,巨大的优势就来了。如果您现在将方法更改为 return List<MyClassChild>
(where MyClassChild
extends MyClass
),您只需更改一处而不是几处。
回答by FD_
The diamond operator is just thought to reduce the unnecessary effort of repeatedly having to type the generic in an assignment.
菱形运算符只是被认为可以减少在赋值中重复键入泛型的不必要努力。
Instead of
代替
ArrayList<MyClassWithThatStupidLongName> list = new ArrayList<MyClassWithThatStupidLongName>();
You could just use:
你可以只使用:
ArrayList<MyClassWithThatStupidLongName> list = new ArrayList<>();
This was however introduced in Java 7, and as you seem to need the code working for a lower version, you'll have to add all those Generics back in, as in my first listing.
然而,这是在 Java 7 中引入的,并且由于您似乎需要为较低版本工作的代码,您必须重新添加所有这些泛型,如我的第一个清单。