20

AFAIK, my class extends parent classes and implements interfaces. But I run across a situation, where I can't use implements SomeInterface. It is the declaration of a generic types. For example:

public interface CallsForGrow {...}

public class GrowingArrayList <T implements CallsForGrow>  // BAD, won't work!
                              extends ArrayList<T> 

Here using implements is syntactically forbidden. I thought first, that using interface inside <> is forbidden at all, but no. It is possible, I only have to use extends instead of implements. As a result, I am "extending" an interface. This another example works:

public interface CallsForGrow {...}

public class GrowingArrayList <T extends CallsForGrow>  // this works!
                              extends ArrayList<T> 

To me it seems as a syntactical inconsistancy. But maybe I don't understand some finesses of Java 6? Are there other places where I should extend interfaces? Should the interface, that I mean to extend, have some special features?

Gangnus
  • 2,805
  • 4
  • 21
  • 31

4 Answers4

25

In the case of generic type variables the compiler doesn't actually care if T is a class, an interface, an enum or an annotation. All it cares about is that it is a type with a given set of sub- and super-types.

And there is no reason to complicate the syntax just because in one other place (where you actually implement an interface) the distinction between classes and interfaces is relevant (for example if you implement an interface, you need to implement all methods it defines, but you don't need to, if you extend a (non-abstract) class).

Assuming for a moment that you'd have to write implements here, then you'd also need a separate syntax for enum values (instead of simply writing <E extends Enum<E>>) and annotations (which you can easily declare using <A extends Annotation>).

The only place where you need to write implements is at the point where you actually implement the interface. At that point (and that point only) the difference is important, because you must implement the methods defined in the interface. For everyone else, it doesn't matter if any given A is a base class or an implemented interface of B: it's a super-type and that's all that matters.

Also note that there's one other place where you use extends with interfaces:

interface A {
}

interface B extends A {
}

At this point implements would be wrong, because B does not implement A.

Joachim Sauer
  • 10,956
  • 3
  • 52
  • 45
  • If we'll use your logics, we should use 'extends SomeInterface' **always**, not only in generics. – Gangnus Feb 29 '12 at 09:02
  • 2
    @Gangnus: no, because for the *implementor* there is a concrete difference between `extends` and `implements`, it's just when looking at the issue from a pure type-system perspective, that there is no difference. – Joachim Sauer Feb 29 '12 at 09:05
  • 1
    Sorry, I do not understand your thought. --1. Why should we use "a pure type-system perspective" in one case and not in the other? --2. Why the syntactic demands change in these different places? Could you explain it, please. In the answer, if possible. – Gangnus Feb 29 '12 at 09:19
  • Thank you for the code example. So other cases exist. But this yours seems logical to me. On the other side, T is a class, not interface. And it implements. – Gangnus Feb 29 '12 at 09:29
  • 1
    @Gangnus: who says that `T` is a class? `T` could reference an interface type or an `enum` type. – Joachim Sauer Feb 29 '12 at 10:03
  • Oh! That the thing I needed to learn, I think. It is the answer. But please, put it in the answer, for other people who will have the same problem. It is not convenient to look for answer in comments. And I can't mark a comment as the answer, too :-) – Gangnus Feb 29 '12 at 11:40
  • @Gangnus: I tried to add that bit of information, please tell me if it's still unclear in my answer. – Joachim Sauer Feb 29 '12 at 12:29
  • Your comments about needing to implement all methods of an interface in the class which declares that it implements it are wrong. An abstract class can declare itself as implementing an interface but leave the actual method implementation to its concrete subclasses. – Peter Taylor Feb 29 '12 at 12:50
  • "(for example if you implement an interface, you need to implement all methods it defines, but you don't need to, if you extend a (non-abstract) class)." Sorry, but T there has to **implement** every member of the interface. So, your logics won't work there? I think , the main thought is that T could be any type, not only class. And if it would be an interface, it should extend, not implement... Any way is bad. – Gangnus Feb 29 '12 at 13:18
  • @Peter: I know, but I don't think that specific detail is relevant to this discussion. In *general* the methods of a *interface* need to be implemented by the class that `implement`s it and *in general* that's not necessary when `extend`ing a class. There are exceptions for both "rules". – Joachim Sauer Feb 29 '12 at 15:43
  • I see and agree. That is why I checked your answer :-). Thank you. – Gangnus Feb 29 '12 at 21:23
  • @Gangnus If you understand the meaning of `extends`, it does not make sense for me to see an `interface` to extend another `interface`. Take for example `public interface List extends Collection{}` Do you mean, `List` is-a `Iterable`, Because `List` is-a `Collection` and `Collection` is-a `Iterable`? i think this is wrong as per this [answer](http://programmers.stackexchange.com/a/262949/131582).If one is getting into a scenario of an `interface` `extends` another `interface`, then it means that already existing design approach was wrong or the current design approach is wrong. – overexchange Dec 12 '14 at 02:46
  • @overexchange *If you understand... it doesn't make sense.* I only see that you are trying to offend me. What did you want to say? – Gangnus Dec 12 '14 at 10:53
  • @overexchange: I too don't get what you are trying to say. But it definitely seems to be unrelated to this question and answer. The question is about why the generics syntax uses `extends` when (potentially) referring to interfaces. Your comment seems to be about the unrelated topic of "should I use interfaces or classes". If you've got a specific question about that, please post that separately. – Joachim Sauer Dec 12 '14 at 11:40
  • @Gangnus sorry for bad english. 1) `` mean ``, `interface` is one type in this case. 2) we already know the scenario of `class xyz implements abc{}`. 3) `interface abc extends def, xyz {}` This is just gathering of methods and nothing more than that. In my previous comment, am trying to say that we get into the scenario as per third point mentioned here, due to design flaw. – overexchange Dec 12 '14 at 13:00
  • 1
    coming from C#, this whole discussion is ridiculous. we denote a type's supertypes with `:`. and under the covers, an interface is and has always been an abstract class with the constraint of only containing unimplemented virtual (`abstract`) members, so as to allow for multiple inheritence. there is literally no difference between `implements` and `extends`. they could both be replaced with the same word (`extends`) or by some arbitrary symbol (`:`) and nothing would be lost. – sara May 20 '16 at 18:15
5

When Java 5, and in particular generics, was initially made available to developers who had registered an interest the syntax was quite different. Instead of Set<? extends Foo> and Set<? super Bar> it had Set<+Foo> and Set<-Foo>. However, the feedback was that it wasn't clear whether + meant more specific or wider (more classes). Sun responded to that feedback by changing the syntax, but within the constraint of not introducing new keywords, which would have been a problem for backwards compatibility.

The result is that neither is quite natural. As you observe, extends is overloaded to talk of classes "extending" interfaces, which isn't the language used in other contexts; and super is overloaded to mean "is a superclass of", which is the opposite direction of the relationship previously expressed by the keyword, i.e. referring to a superclass.

However, the fundamentals of what an interface is are not affected by this change, and it doesn't introduce special interfaces which are extended in a new way.

Peter Taylor
  • 4,012
  • 1
  • 24
  • 29
  • +1. I see and agree. But Joachim Sauer has found my erroneous thinking that T is necessarily a class. So, the answer is his. Your understanding is one(or 2) storey higher :-). My problem was more primitive. Thank you anyway for my development. – Gangnus Feb 29 '12 at 13:23
2

There are disadvantages in both allowing and prohibiting such syntax, and those of allowing are far greater.

Just think of it.

Separation of interface and implementation is one of fundamental programming idioms. Because of that, syntax allowing to spell "interface implements something" would be about as bad as one using plus sign to denote multiplication of operands.

gnat
  • 21,442
  • 29
  • 112
  • 288
  • Ok. So, I really do not understand something. I considered it very probable. But you haven' explained the problem at all, sorry. T is a representation of a class. Why in one place I use T extends and in another T implements? – Gangnus Feb 29 '12 at 11:37
  • @Gangnus in the example you provided T refers to _type parameter_ which is not necessarily a class - [see what Joachim told you already](http://programmers.stackexchange.com/questions/137501/who-extends-interfaces-and-why/137527#comment258590_137502). Allowing _implements_ for it would lead to the same mess I mentioned – gnat Feb 29 '12 at 11:48
  • Yes, I have seen already his comment. It will be marked as the answer when put in answer. Till that you both have my thanks and +1. – Gangnus Feb 29 '12 at 11:51
-1

One needs to understand interface driven programming as next step while understanding an interface. It tell what is actual use of interface. What role it plays in a Java (or any other language) program.

Deepak
  • 1
  • 2
    How does your answer address the OP's concerns? Please [edit] your answer to be more clear. –  Jul 01 '13 at 14:15