enforce override of method

M

Mize-ze

Hi,
Let's say I have a class A which implements interface I, which has a
method foo() in it,
I want (and I must) implement I.foo() method in class A.

Now, I have a Class B which extends A and therefore inherits it's
foo() method. however,
I don't want class B to use A's implementation of foo() but instead
implement its own .
I can easily just override the method by implementing the foo() method
in B.

BUT what if I want to enforce the user to implement foo()?
Anyway of doing this?
It's like having class A as abstract class( foo() as abstract). but it
isn't...

Thanks.
 
M

Matt Humphrey

| Hi,
| Let's say I have a class A which implements interface I, which has a
| method foo() in it,
| I want (and I must) implement I.foo() method in class A.
|
| Now, I have a Class B which extends A and therefore inherits it's
| foo() method. however,
| I don't want class B to use A's implementation of foo() but instead
| implement its own .
| I can easily just override the method by implementing the foo() method
| in B.
|
| BUT what if I want to enforce the user to implement foo()?
| Anyway of doing this?
| It's like having class A as abstract class( foo() as abstract). but it
| isn't...

If B must extend A and foo must be accessible outside of the package, there
is no way to enforce that B.foo() not override or use A.foo(). If there
were a way to enforce it, B could always write a method fooAlt () which
calls foo() (because foo is accessible) and then let B.foo () "override" by
calling fooAlt().

If foo can be restricted to the package, A can give it default protection.
n that case B would then not have any access to it, but no code outside of
the package could use A.foo either. B.foo would be available, but it would
be different from A.foo and would not override it.

Matt Humphrey (e-mail address removed) http://www.iviz.com/
 
M

Mize-ze

| Hi,
| Let's say I have a class A which implements interface I, which has a
| method foo() in it,
| I want (and I must) implement I.foo() method in class A.
|
| Now, I have a Class B which extends A and therefore inherits it's
| foo() method. however,
| I don't want class B to use A's implementation of foo() but instead
| implement its own .
| I can easily just override the method by implementing the foo() method
| in B.
|
| BUT what if I want to enforce the user to implement foo()?
| Anyway of doing this?
| It's like having class A as abstract class( foo() as abstract). but it
| isn't...

If B must extend A and foo must be accessible outside of the package, there
is no way to enforce that B.foo() not override or use A.foo(). If there
were a way to enforce it, B could always write a method fooAlt () which
calls foo() (because foo is accessible) and then let B.foo () "override" by
calling fooAlt().

If foo can be restricted to the package, A can give it default protection.
n that case B would then not have any access to it, but no code outside of
the package could use A.foo either. B.foo would be available, but it would
be different from A.foo and would not override it.

Matt Humphrey (e-mail address removed)://www.iviz.com/

Hi Matt,
I'm afraid I wasn't that clear,
I want to have a situation where if one of my developers wants to
extend A he HAS to override
foo() and not use A's implementation (although he can trick the system
by calling it at fooAlt, that's fine by me...)

Bottom line:
I want he's class not to compile until he implements foo().
 
T

Twisted

If B must extend A and foo must be accessible outside of the package, there
is no way to enforce that B.foo() not override or use A.foo(). If there
were a way to enforce it, B could always write a method fooAlt () which
calls foo() (because foo is accessible) and then let B.foo () "override" by
calling fooAlt().

If foo can be restricted to the package, A can give it default protection.
n that case B would then not have any access to it, but no code outside of
the package could use A.foo either. B.foo would be available, but it would
be different from A.foo and would not override it.

Rethink the class hierarchy. What you want isn't I->A->B; you want

-> A
I -> ABase
-> B

with ABase having an abstract foo() method and otherwise all the code
of your original A class, and A just being a final subclass with an
implementation of foo. Anyone who wants to make B has to subclass
ABase instead of A (which is final), and then override foo (which is
abstract), and can't use super.foo (since it's abstract) or A.foo
(which is not applicable to "this").
 
Z

Zig

Inheritence can't give you what you are looking for, but if you consider
delegation, you might get the desired effect.

eg:

public class A implements I {
private final I _delegate;
protected A(I imp) {
if (imp==null) throw new NullPointerException();
_delegate=imp;
}
public void foo() {
_delegate.foo();
}
public static A createDefaultA() {
return new A(new I() {
public void foo() {
// default foo method
});
}
}
 
Z

Zig

Just forgot the more obvious, if you are willing to make A abstract, you
can also make it a factory with an anonymous implementation

public abstract class A implements I {
protected A() {
}
public static A createDefaultA() {
return new A() {
public void foo() {
//default foo
}};
}
}

Now, subclass B must implement foo, but users can still get a reasonable
default implementation (not elsewhere exposed or inheritable).
 
I

Ingo R. Homann

Hi Mize-ze,
Rethink the class hierarchy. What you want isn't I->A->B; you want

-> A
I -> ABase
-> B

with ABase having an abstract foo() method and otherwise all the code
of your original A class, and A just being a final subclass with an
implementation of foo. Anyone who wants to make B has to subclass
ABase instead of A (which is final), and then override foo (which is
abstract), and can't use super.foo (since it's abstract) or A.foo
(which is not applicable to "this").

I'm not sure if you are aware that the following solution is also
possible (although I suspect that Twisted's or Zig's solution might be
the better one for your problem):


interface I {
void foo();
}

class A implements I {
public void foo() {}
}

abstract class B_Base extends A {
public abstract void foo();
}

class B extends B_Base {
// compiler error: foo() not implemented!
}


Ciao,
Ingo
 
T

Twisted

I'm not sure if you are aware that the following solution is also
possible (although I suspect that Twisted's or Zig's solution might be
the better one for your problem)

I've now seen Zig's posting, and he eventually arrived where I did by
a circuitous route, aside from his A being an anonymous implementation
returned by an ABase factory method instead of a standalone public
final class. (My names for the classes but describing his structure.)
class A implements I {
public void foo() {}

}

abstract class B_Base extends A {
public abstract void foo();

}

class B extends B_Base {
// compiler error: foo() not implemented!

}

Nothing here is stopping someone directly extending A. And A can't be
made final or B_Base can't exist.

A could be given only package-private constructors and B_Base (in the
same package) a protected or public one. Then it more-or-less works,
unless someone's willing to define their class into someone else's pre-
existing package. :)

However, my version gives what I feel to be a cleaner type hierarchy
-- logically, there is A-that-can-be-extended-but-requires-foo-
implementing and A-that-is-a-directly-usable-implementation.
Separating those into abstract ABase and final A tidies up and keeps
what should be subclassed determined by "final" rather than
constructor hijinks.

And of course anyone who mentions that A's constructor could have code
like "if (!(getClass().equals(A.class)) && !(this instanceof B_Base))
throw..." will be flamed to a crispy br<claps hands over mouth and
turns red>
 
I

Ingo R. Homann

Hi Twisted!
Nothing here is stopping someone directly extending A. And A can't be
made final or B_Base can't exist.

Well, of course, Mize-ze has to provide B_Base, so it *will* exist. The
other point (directly extend A) is true but can be solved as you showed
(package-private constructor). Anyhow...
However, my version gives what I feel to be a cleaner type hierarchy
-- logically, there is A-that-can-be-extended-but-requires-foo-
implementing and A-that-is-a-directly-usable-implementation.
Separating those into abstract ABase and final A tidies up and keeps
what should be subclassed determined by "final" rather than
constructor hijinks.

....I totally agree to this. (That was what I meant with "Twisted's ...
solution might be the better one".)
And of course anyone who mentions that A's constructor could have code
like "if (!(getClass().equals(A.class)) && !(this instanceof B_Base))
throw..."...

:)

Ciao,
Ingo
 
S

stefanomnn

Hi,
Let's say I have a class A which implements interface I, which has a
method foo() in it,
I want (and I must) implement I.foo() method in class A.

Now, I have a Class B which extends A and therefore inherits it's
foo() method. however,
I don't want class B to use A's implementation of foo() but instead
implement its own .
I can easily just override the method by implementing the foo() method
in B.

BUT what if I want to enforce the user to implement foo()?
Anyway of doing this?
It's like having class A as abstract class( foo() as abstract). but it
isn't...

Thanks.

in implementation of foo in class A,
try so:

if(this.getClass().equals(A.class)==false) {
// "this" is an instance of a sub-class
throw new NoSuchMethodException();
}
 
M

Mize-ze

I've took your advice and did some re-thinking.
I made an abstract ABase with abstract foo()

So now my A and any other "ABases" (such as B) will directly extend
ABase.

Thanks
 
P

Philipp Leitner

in implementation of foo in class A,
try so:

if(this.getClass().equals(A.class)==false) {
// "this" is an instance of a sub-class
throw new NoSuchMethodException();

}

This looks like awful design, and it won't do what the OP wanted. This
solution will just throw an Runtime Exception, while the OP wanted a
statically safe solution.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,769
Messages
2,569,580
Members
45,054
Latest member
TrimKetoBoost

Latest Threads

Top