在下列情况下,我遇到问题,请查看下面的内联评论:
public void exampleMethod() {
//Intuitively I would expect this to mean that test is set containing objects
//that subclass AbstractGroup
Set<? extends AbstractGroup> test;
//Yet the compiler complains here and I do not understand why?
test.add(new AnyAbstractGroupSubGroup());
//I would guess that a method call such as this at runtime
test = new HashSet<SubGroupA>()
//would mean that only objects of subgroupA can be added to the collection, but then
//what is the point in using the wildcard in the first …Run Code Online (Sandbox Code Playgroud) 这是Java在多级层次结构中继承Fluent方法返回类型的简化版本.
给出以下代码:
public enum X {
;
static interface BaseFoo<T, S extends BaseFoo<T, S>> {
S foo();
}
static interface Foo<T> extends BaseFoo<T, Foo<T>> {
void foo1();
}
static interface BaseBar<T, S extends BaseBar<T, S>> extends BaseFoo<T, S> {
S bar();
}
static interface Bar<T> extends BaseBar<T, Bar<T>>, Foo<T> {
void bar1();
}
}
Run Code Online (Sandbox Code Playgroud)
运行javac X.java我收到错误消息:
X.java:15: error: BaseFoo cannot be inherited with different arguments: <T,X.Bar<T>> and <T,X.Foo<T>>
static interface Bar<T> extends BaseBar<T, Bar<T>>, Foo<T> { …Run Code Online (Sandbox Code Playgroud) 阅读书籍Java Generics and Collections.在Wildcards with Super一节中,我举了一个例子
public static <T> void copy(List<? super T> dst, List<? extends T> src) {
for (int i = 0; i < src.size(); i++) {
dst.set(i, src.get(i));
}
}
Run Code Online (Sandbox Code Playgroud)
它被称为这样:
Collections.<Number>copy(objs, ints);
Run Code Online (Sandbox Code Playgroud)
以上电话有效,其解释如下:
允许调用因为
objs有类型List<Object>,它是List<? super Number>(因为Object是Number通配符所需的超类型)的子ints类型List<Integer>,并且具有类型,它是List<? extends Number>(因为Integer是Number扩展通配符所需的子类型)的子类型
我的疑问是怎样List<Object>的一个亚型 List<? super Number>?
这是我的代码:
Set<Class<Event>> s = new HashSet<>();
Set<Class<? extends Event>> s2 = new HashSet<>();
Event e = new Event();
s.add(e.getClass()); // #1
s2.add(e.getClass()); // #2
class Event {
// ...
}
Run Code Online (Sandbox Code Playgroud)
为什么编译器会在语句中引发错误#1?
我正在使用Java 7.
我使用cqengine进行集合索引:
Attribute<UtilizationEntry, LocalDate> startDateAttr = new SimpleAttribute<UtilizationEntry, LocalDate>() {
@Override
public LocalDate getValue(UtilizationEntry object, QueryOptions queryOptions) {
return object.getStartDate();
}
};
IndexedCollection<UtilizationEntry> entries = new ConcurrentIndexedCollection<>();
entries.addIndex(NavigableIndex.onAttribute(startDateAttr)); // compilation error in this line
Run Code Online (Sandbox Code Playgroud)
此代码未编译,因为:
Error:(61, 70) java: no suitable method found for onAttribute(com.googlecode.cqengine.attribute.Attribute<entities.UtilizationEntry,java.time.LocalDate>)
method com.googlecode.cqengine.index.navigable.NavigableIndex.<A,O>onAttribute(com.googlecode.cqengine.attribute.Attribute<O,A>) is not applicable
(inferred type does not conform to equality constraint(s)
inferred: java.time.chrono.ChronoLocalDate
equality constraints(s): java.time.chrono.ChronoLocalDate,java.time.LocalDate)
method com.googlecode.cqengine.index.navigable.NavigableIndex.<A,O>onAttribute(com.googlecode.cqengine.index.support.Factory<java.util.concurrent.ConcurrentNavigableMap<A,com.googlecode.cqengine.resultset.stored.StoredResultSet<O>>>,com.googlecode.cqengine.index.support.Factory<com.googlecode.cqengine.resultset.stored.StoredResultSet<O>>,com.googlecode.cqengine.attribute.Attribute<O,A>) is not applicable
(cannot infer type-variable(s) A,O
(actual and formal argument lists differ in length)) …Run Code Online (Sandbox Code Playgroud) 一种Java reduce方法Stream:
<U> U reduce(U identity,
BiFunction<U, ? super T, U> accumulator,
BinaryOperator<U> combiner);
Run Code Online (Sandbox Code Playgroud)
有助于根据流中对象的某些属性来减少流.
但是,我不清楚为什么accumulator不能更直接和服务于同一目的:
BiFunction<U, T, U> accumulator.
accumulator签名中的通配符提供了哪些额外的灵活性(以降低可读性为代价)?
java支持class Foo<T super X>,如果没有,为什么?
其中T是类型参数,X是类型.
在Java 8中,类java.util.Optional(javadoc)类提供"Maybe"Monad或Option Type的功能.
更直接:
public final class java.util.Optional <T> extends Object
容器对象,可能包含也可能不包含非null值.如果存在值,则isPresent()将返回true,get()将返回该值.
其中一种方法是:
<U>可选<U>地图(功能<?super T,?extends U> mapper)
如果存在值,则将提供的映射函数应用于该值,如果结果为非null,则返回描述结果的Optional.
问题是为什么map()在类型上使用类型通配符U.
我对类型通配符的理解很简单:
? super T从指定从该组由子类路径给定类型的一些Object到T(两者Object并T包括)联合在拉出任何subinterfacing路径上找到的组接口"作为sidedish"通过implements.
并? extends U简单地从扩展U(U包括)的类集合中指定一些类型.
所以可以写一下:
<U>可选<U>地图(功能<?super T,U> mapper)
没有丢失信息.
或不?
我正在学习 Java 中的泛型,我正在学习协方差和逆变。我了解协方差,为什么我们不能写入协方差类型。但对我来说,逆变是令人困惑的。我想知道为什么从逆变读取总是对象类型
假设我们有以下课程
Class Animal
Class Dog extends Animal
Class Tiger extends Animal
Run Code Online (Sandbox Code Playgroud)
现在,考虑以下代码
List<Animal> animals = new ArrayList<>();
List<? super Animal> contraVarianceList=animals;
animals.add(new Dog()); // Allowed
animals.add(new Tiger()); //Allowed
Animal animal = contraVarianceList.get(0); // Not allowed. Why?
Run Code Online (Sandbox Code Playgroud)
我的问题是为什么我们不能从逆变列表中读取“动物”。为什么总是而且只有“Object”可以返回?如果我们从逆变列表中读取“Animal”,将会或可能会出现什么问题?
希望在了解通用边界之后,我尝试了解通配符上限和下限。我的参考是: https: //docs.oracle.com/javase/tutorial/java/generics/wildcards.html 我发现有一句话我能理解:“通配符可以在多种情况下使用:作为参数、字段或局部变量; “字段和局部变量?无法想象。为什么如此重要的来源不通过一个简单的例子来强调它?
我试图了解 java 编译器用哪个引用来替换(同时擦除)“?”。也许我有一个很大的误解,并且会发生任何删除(因此以下所有示例都不相关)。在下面的例子中: 1.
public static void funcA (List<? extends Number>l)
Run Code Online (Sandbox Code Playgroud)
2.
public static void funcB(List<? super Integer>l)
Run Code Online (Sandbox Code Playgroud)
第二个示例和以下代码之间有区别吗: 3.
public static <T extends Integer> funcC(List<? extends T>l)
Run Code Online (Sandbox Code Playgroud)
示例2与下面的示例是否有不同: 4.
public static <T extends Integer> void funcC(List<T>l)
Run Code Online (Sandbox Code Playgroud) generics ×10
java ×10
collections ×2
java-8 ×2
cqengine ×1
fluent ×1
inheritance ×1
type-erasure ×1
wildcard ×1