Hi,

Sometimes I miss a feature in generic type declarations where one could refer to a type variable of a super type without repeating it in the declaration of the generic type. For example, currently one has to write:


interface Snapshooter<E, C extends Collection<E>> {
    C snapshot();
    boolean addElement(E e);
}

Snapshooter<String, List<String>> strings = ...;

List<String> snapshot1 = strings.snapshot();
strings.addElement("abc");
List<String> snapshot2 = strings.snapshot();


What if E could be implicitly declared like:

interface <E> Snapshooter<C extends Collection<E>> {
    C snapshot();
    boolean addElement(E e);
}

Snapshooter<List<String>> strings = ...;


Which would be similar to declaring:

interface Snapshooter<C extends Collection<?>> { ... }

...with added benefit that one could refer to E from Collection<E>.


I don't know if this could be soundly incorporated into the language type system, but if it could be, and if interfaces could also be implemented by value types, then...

On 12/19/2015 05:38 PM, Brian Goetz wrote:
Anyfy equals, and adjust default implementation of boolean T.equals(any x)

I think we may be talking past each other (while basically saying the same thing from opposite directions.)

"any" is not a type; it is a modifier that affects the domain of type variables. So we don't have (and I think we don't want) a meaning for equals(any x). But what we do want, is a way of expressing "I'll take anything which could be on the other side of the == operator with me." For refs, that's Object; for a value type V, that's just V.

Where we had gotten with the <V super U> / superation idiom (not suggesting either of these syntaxes is great) is being able to express:

 - If T is value, then T, else the erasure of T (usually object) **

I'll write this as Sup<T> for short. The convenient thing about Sup<T> is that it conveniently collapses to Object in the places where we want Object, so we could define contains/remove as

  contains(Sup<T>)

and contains will always bottom out at equals(), so equals() similarly needs to be

  equals(Sup<Self>)

If this is a valid approach (and I think its the best one we've got so far), then we're looking for how to spell Sup<Self> (in all of: type system, language syntax, bytecode descriptors.)


....there could be a special interface:

public interface Any<any T extends Any<T>> {
    boolean equals(T x);
}


...implemented by Object:

public class Object implements Any<Object> {...}

...and implicitly implemented by every value type:

public value ValueType [ implements Any<ValueType> ] {...}


Sup<E> from Collection<any E> could then be expressed as:

public interface <T> Collection<any E extends Any<T>> extends Iterable<E> {
    boolean contains(T x);
    ...


Regards, Peter


I still think that doing something like this removes the need
to specially deal with Collection.contains and related methods.

I don't see it yet; those signatures are still currently contains(Object), which isn't appropriate for value types. So we have to do *something*.




** There's a lot of sloppiness in the ref/val distinction, which is going to need to be cleaned up. Sometimes when we say ref/val, we mean "erased/reified". Sometimes we mean "polymorphic/monomorphic". Sometimes we mean "nullable/non-nullable."

Reply via email to