Why not make the return type <T extends This>?

~~ Robert.

joel.neely wrote:
> In the interest of fairness to Good Old Java, this is not as much of a
> show-stopper as the examples make it appear.
> 
> On Feb 13, 10:14 pm, Jeff Grigg <[email protected]> wrote:
>> The problem is that when you use method chaining on classes that
>> extend other classes and which add methods, you MUST always call
>> subclass methods before calling superclass methods -- otherwise it
>> won't compile.
> 
> First, we can go a tad further than the parent post's example; as Jeff
> showed, even though this
>         new Sub().setSubStuff().setBaseStuff();
> will compile, this
>         new Sub().setBaseStuff().setSubStuff();
> will not. Even worse, this
>         Sub badSub = new Sub().setSubStuff().setBaseStuff();
> won't either!
> 
> Oh, horrors! Java is completely broken!  (I'm kidding! ;-)
> 
> Back in Java 101, we learned that Java allows implicit upcasting, but
> requires explicit downcasting. The compiler barfs on the second line
> of this:
>         Base stealthSub = new Sub();
>         Sub notSub = stealthSub;
> but uncomplaingly takes this:
>         Base stealthSub = new Sub();
>         Sub notSub = (Sub) stealthSub;
> because the programmer took responsibility for guaranteeing the
> appropriate relationship.
> 
> So, back to the original examples, this:
>         Sub badSub = new Sub().setSubStuff().setBaseStuff();
> fails because in the general case setBaseStuff() might really return
> an instance of Base that is incompatible with Sub. But the programmer
> can write code that explicitly states her/his intentions and gives the
> compiler a promise of type-safe behavior, as in:
>         Sub goodSub = (Sub) new Sub().setSubStuff().setBaseStuff();
> 
> The same solution applies to the chained methods; I simply guarantee
> the compiler that I haven't broken the "chain of possession" with a
> cast, either for the assignment to a variable of type Sub:
>         Sub goodSub = (Sub) new Sub().setSubStuff().setBaseStuff();
> or within the sequence of chained method calls:
>         ((Sub) new Sub().setBaseStuff()).setSubStuff();
> both of which DO compile.
> 
> So, its a bit of an exaggeration to imply that we CAN'T call Sub
> methods first. We simply have to be explicit when the instance sheds
> its Base overcoat. (I'm not going to mention monads here! ;-)
> 
> Do I think this solution is beautiful and graceful and effortless? Not
> really. But it does allow us:
> - to compile our code,
> - to talk fearlessly about the various orderings of builder method
> calls and whether there are some good practice statements waiting to
> emerge,
> - to calmly examine new language proposals while continuing to write
> and compile code that is explicit and works, and,
> - (most importantly, IMHO) to avoid completely changing the meaning of
> void from "nothing will be returned".
> 
> I regard the redefinition of void to be a much greater threat to the
> readability of Java than the need to insert an explicit cast now and
> then.
> 
> -jn-
> 
> > 
> 

-- 
~~ Robert Fischer.
Grails Training        http://GroovyMag.com/training
Smokejumper Consulting http://SmokejumperIT.com
Enfranchised Mind Blog http://EnfranchisedMind.com/blog

Check out my book, "Grails Persistence with GORM and GSQL"!
http://www.smokejumperit.com/redirect.html

--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups "The 
Java Posse" group.
To post to this group, send email to [email protected]
To unsubscribe from this group, send email to 
[email protected]
For more options, visit this group at 
http://groups.google.com/group/javaposse?hl=en
-~----------~----~----~----~------~----~------~--~---

Reply via email to