我对接口和继承在实现阶段的工作方式感到有些困惑。这是一个快速的ERD:
<<interface>>
Animal IColorChangable
---------------------------- -----------------------
-color: int -----------------------
---------------------------- + changeColor()
---------------------------- -----------------------
^(Inheritance Triangle) ^(Interface Triangle)
| |
| |
----------------------------------------------
Dog
----------------------------
-breed: string
----------------------------
+ getBreed()
----------------------------
所以这里我有一条狗,它扩展了一个Animal类,并且还实现了一个ColorChangable接口。现在,颜色可变界面的工作是更新颜色,这是属于动物的属性,而不是狗。那么更新dog类中颜色的正确方法是什么?它是实现颜色变化的狗,而不是动物。现在我有这个:
public class Dog extends Animal implements IColorChangable
{
private String breed;
public Dog(int color, String breed)
{
super(color);
this.breed = breed;
}
public void changeColor()
{
//How to have access to color?
}
}
public interface IColorChangable
{
public void changeColor();
}
答案 0 :(得分:3)
所以你只需要将setColor和getColor添加到Animal类中,但是你应该将它们定义为公共方法。
public void setColor(int color){
this.color = color;
}
public int getColor(){
return color;
}
然后在changeColor中,您可以通过setColor填充颜色。
public void changeColor()
{
setColor(10); //for example
}
答案 1 :(得分:2)
你基本上有三种选择。您选择哪个取决于您的要求,不变量的复杂性等等。
第一个选项是在color
中将protected
声明为Animal
,然后您可以直接在派生类中访问它:
public class Animal {
protected int color;
...
}
public class Dog extends Animal implements IColorChangable {
...
@Override public void changeColor () {
color = ...;
}
}
第二个选项是在private
中声明它Animal
,在这种情况下,您无法直接使用子类访问它,但您可以将一个setter添加到Animal
(可选{{}} 1}},可选final
,再次取决于您的规则)。例如,如果要在基类中实现通用验证逻辑,这将非常有用:
protected
第三个选择是考虑这个问题:每个动物的颜色都可以改变吗? (在您的示例中,public class Animal {
private int color;
...
protected final void setColor (int color) { // could be public, could be non-final
this.color = color;
}
}
public class Dog extends Animal implements IColorChangable {
...
@Override public void changeColor () {
setColor(...);
}
}
是一般color
的属性。)如果是,那么您可以Animal
实现接口:
Animal
这实际上取决于你需要做什么。
顺便说一下,在Java中使用public class Animal implements IColorChangable {
private int color;
...
@Override public void changeColor () {
color = ...;
}
}
public class Dog extends Animal {
...
}
启动接口名称并不是通常传统。我们通常也使用“属性”而不是“属性”。 :)
答案 2 :(得分:1)
color = 123;
但您的属性颜色必须设置为公开或受保护。
如果它是私有的,你需要在Animal类中设置一个setter:
public void setColor(int color){
this.color = color;
}
然后在你的方法中调用它:
setColor(color);
答案 3 :(得分:0)
只需将其作为普通会员访问:
public void changeColor(int color)
{
this.color = color;
}