2017-07-19 19 views
2

我编写了一个简单的接口继承示例来说明我正在尝试执行的操作。调用/分配实现接口的类的变量

interface Fruit{ 
    public void taste();  
} 


class Banana implements Fruit { 
    public String name = "Banana"; 
    public void taste(){ 
     System.out.println("yummy banana!"); 
    } 


class Strawberry implements Fruit { 
    public String name = "Strawberry"; 
    public void taste(){ 
     System.out.println("yummy strawberry!"); 
    } 
} 

class Lunch<Fruittype implements Fruit> { 
    public Fruittype fruit; 

    public void tasteit() { 
     System.out.println("I'm going to eat a"+ fruit.name + "!"); 
     // error: name cannot be resolved or is not a field 
     fruit.taste(); 
    } 
} 

class exec { 
    public static void main(String[] args) { 
      Lunch<Banana> bananalunch = new Lunch<>; 
      bananalunch.fruit = new Banana(); 
      bananalunch.tasteit(); 
    } 
} 

所以香蕉和草莓正在实施水果。在课程午餐中,我试图称之为水果名称及其功能品味(); 虽然调用函数的味道工作得很好,我不能称为名称(请参阅:在评论中的错误)

通缉输出: 我要去吃香蕉! 美味的香蕉!

就像我说的,美味的香蕉的作品,但名称无法解决。我试图声明“public String name =”default“”;在水果界面。然后你可以调用它,但它总会说“默认”,而不是实际课程中的名称。

有没有办法获得实现接口的泛型类型的成员? P.S.我需要这样做,当然这个代码只是为了表示,但我有一个更复杂的代码,我遇到了这个问题 - 我不想重构它,如果不是必要的。

预先感谢您!

+4

我会为接口添加一个'getName()'方法,并在该接口的实现中实现标准的getter/setter方法。 (当然,使'name'私密。) – David

回答

3

您的问题是由于尝试直接访问实例成员而导致的 - fruit.name - 而不是通过方法 - fruit.getName()

如果使用getter方法,将会执行正确的方法并返回所需的输出。

也就是说,在这个特定的例子中,在基类中有一个单一的getName()方法,并且在该基类中有一个单一的_name变量,它被初始化为基于实际类型的不同值水果类。

另一方面,看到您的Fruit是一个接口而不是基类,您可以让每个实现该接口的类都有一个返回不同值的getName()方法。

例如:

class Strawberry implements Fruit { 
    public String name = "Strawberry"; 
    public void taste(){ 
     System.out.println("yummy strawberry!"); 
    } 
} 

将成为:

class Strawberry implements Fruit { 
    public String getName() { 
     return "Strawberry"; 
    } 
    public void taste() { 
     System.out.println("yummy strawberry!"); 
    } 
} 

你将不得不增加getName()到接口:

interface Fruit { 
    public String getName(); 
    public void taste();  
} 

最后,您Lunch类变为:

class Lunch<Fruittype implements Fruit> { 
    public Fruittype fruit; 

    public void tasteit() { 
     System.out.println("I'm going to eat a "+ fruit.getName() + "!"); 
     fruit.taste(); 
    } 
} 
+0

谢谢!我没有想过这个 – kalu

0

当类实现接口时,意味着这个类的对象可以做一些在接口中描述的事情。

例如,每个平面形状都有面积。所以我们可以确定接口:

interface PlaneShape { 
    int getArea(); 
} 

正方形区域是边缘的乘积。圈的面积是 平方半径乘pi数除以2的乘积。所以:

class Square implements PlaneShape { 
    public int edge = 5; 

    public int getArea() { 
     return edge*edge; 
    } 
} 

class Circle implements PlaneShape { 
    public int radius = 5; 
    public int pi = 3.14; 

    public int getArea() { 
     return radius*radius*pi/2; 
    } 
} 

接口用于抽象。 AreaCalculator使用平面形状进行操作,因此它可以从任何特定类型的平面形状中抽象出来。 AreaCalculator只知道任何形状都可以通过执行方法getArea()来给他面积值。 AreaCalculator不知道特殊形状字段的任何内容,如edgeradius

class AreaCalculator<S implemets PlaneShape> { 
    public S shape; 

    public int calculateArea() { 
     shape.getArea(); 
    } 
} 

通过这种方式,在你的榜样,Lunch<Fruittype implements Fruit>类不知道什么水果在内的名称,它不“看”这个领域,它只能祈求的方法taste()。您需要添加方法getName()来接口并实现它。

关于name="default"的主题在界面中。它在接口的上下文中声明并且与实现没有任何关系。

相关问题