tags:

views:

204

answers:

5

Why are protected members allowed in final classes?

Shouldn't this be a compile-time error?

Edit: as people have pointed out, you can get same package access by using the default modifier instead. It should behave in exactly the same manner, because protected is just default + sub-classes, and the final modifier explicitly denies subclassing, so I think the answer is more than just to provide same package access.

+12  A: 

Because protected members can be accessed by other classes in the same package, as well as subclasses.

skaffman
Certainly true, though if that's the case you get the same result using the default (package) access, so it could still be a compile error. I think this is just more evidence that they should have kept subclass visibility and package/inner-class visibility as completely separate concepts. Who are they to tell me that if a subclass has visibility, the package must also?
Mark Peters
@Mark: Yeah, it clearly wasn't thought through as well as it could be.
skaffman
"protected members can be accessed by other classes in the same package" :O really?! I thought that's what package-private was for?
Coronatus
@Coronatus, see the JLS 6.6.1, http://java.sun.com/docs/books/jls/third_edition/html/names.html#6.6.1 . \ @Mark Peters, agreed, and package access should not be the default.
Andy Thomas-Cramer
@Coronatus: It is. But so is `protected`.
skaffman
+7  A: 

The protected modifier also allows access within the same package, not just to subclasses. So it's not completely meaningless on a final class.

Affe
30 seconds too sloooooooow :(
Affe
A: 

You can argue that, but there's no real harm anyway. A non-final class may also have a protected member, but no subclass, it won't bother anybody either.

irreputable
Things that can be proven useless are good candidates for compile errors (warnings would be better) not because they directly "bother" or "hurt" anybody/anything, but rather because there's a very high likelihood of it being a programmer mistake/typo.
Mark Peters
how can you prove it's useless? change a final class to a non final class does not even break binary compatibility.
irreputable
+6  A: 

The argument stated here that protected members can be accessed by classes of the same package is valid, but in this case protected becomes equal to the default visibility (package-private), and the question remains - why are both allowed.

I'd guess two things:

  • no need to forbid it
  • a class may be made final temporarily, until a design decision is made. One should not go and change all visibility modifiers each time he adds or removes final
Bozho
+1: I was however surprised how quick the "incorrect" answers got upvoted. Does it tell something about the average knowledge?
BalusC
+11  A: 

The protected modifier is necessary on methods that override protected methods from a base class, without exposing those members to the public.

In general, you could introduce a lot of unnecessary rules to outlaw implausible combinations (such as protected static), but it wouldn't help much. You can't outlaw stupidity.

Tom Hawtin - tackline
Ah, ok. Because you can't reduce the visibility to make them default or private (which is probably what is intended in a final class), so you can leave them protected or expose them as public. Although in this case making them default does NOT reduce the visibility (since no subclassing is possible), so IMHO the compiler should stop whining.
Tom Tresansky
@Tom Yes. I should have said you could make them `public` but you wouldn't want to. Actually `protected` behaves peculiarly if you override in a different package. I'm not a fan of `protected`.
Tom Hawtin - tackline
@Tom: Good point, methods are members too! Solid counter-example.
Mark Peters