我无法调用在子类中定义的方法。

huangapple go评论61阅读模式
英文:

I can't invoke the method defined in the subclass

问题

I have 2 classes:

public class Animal {
	
	protected String name;
	int age;
	
	public Animal(String name, int age) {
		// TODO: Constructor logic here
		
		this.name = name;
		this.age = age;
	}
	
	public static void eating() {
		System.out.println("eating");
	}
}
public class Human extends Animal {

	public Human(String name, int age) {
		// TODO: Constructor logic here
		super(name, age);
	}
	
	public static void talking() {
		System.out.println("Talk");
	}
}

Main program:

public class program {
	
	public static void main (String [] args) {
	
		Animal hum = new Human("bob", 1);
		
		System.out.println(hum);
		//hum.talking();
		
	}
}

The output of the main program is wk05.Human@7f690630. So why I can't do "hum.talking" in the main program? My understanding of inheritance is that the subclass can invoke the methods defined in the parent class as well as the method defined in the subclass.

英文:

I have 2 classes:

public class Animal {
	
	protected String name;
	int age;
	
	
	public Animal(String name, int age) {
		// TODO Auto-generated constructor stub
	
		this.name = name;
		this.age = age;
	}
	
	public static void eating() {
		System.out.println("eating");
	}
}

public class Human extends Animal{

	public Human(String name, int age) {
		// TODO Auto-generated constructor stub
		super(name, age);
	}
	
	
	public static void talking() {
		System.out.println("Talk");
	}
}

main program:

public class program {
	
	public static void main (String [] args) {
	
		Animal hum = new Human("bob", 1);
		
		System.out.println(hum);
		//hum.talking();
		
	}

}

The output of the main program is wk05.Human@7f690630. So why I can't do "hum.talking" in the main program? My understanding of inheritance is that the subclass can invoke the methods defined in the parent class as well as the method defined in the subclass.

答案1

得分: 1

在你的程序中,Animal hum = new Human("bob", 1); 表示 hum 引用了 Animal 超类,该超类没有定义 talking() 方法,而对象是 Human

在编译时,引用被视为对象,但在运行时使用对象。因此,如果你想调用 talking() 方法,你需要:

1) 创建对 Human 类的引用
在这里,引用也是对 Human 类的引用,所以它在编译时具有 talking() 方法的定义。

Human hum = new Human("bob", 1);
hum.talking();

2) 将对象强制转换为 Human(仅用于理解类型转换)
当我们将对象强制转换时,我们明确告诉编译器引用已定义的对象。这样它就可以引用它。

Animal hum = new Human("bob", 1);
((Human) hum).talking();

其背后的原因是,假设你有另一个类 SuperHuman,它也扩展了 Animal 类,但该类没有 talking() 方法,那么编译器怎么知道引用 hum 将引用 Human 还是 SuperHuman 呢?

再假设在初始化时我们这样做了 Animal hum = new Human("bob", 1);,然后在代码中将 hum 更新为 hum = SuperHuman("sup", 10);。这就是编译时引用在运行时引用对象的原因。

英文:

Here in your program Animal hum = new Human("bob", 1); means hum reference to Animal super class which does not have definition of talking() and object is Human.

At compile time reference is considered rather than the object. Object is used at runtime. So if you want to call talking() you would need to:

1) Create reference to Human class
Here the reference is also to Human class so it has the definition of talking() method at compile time.

Human hum = new Human("bob", 1);
hum.talking();

2) Cast object to Human (only for understanding the type-casting)
When we cast the object we explicitly tell the compiler to refer the defined object. So it can refer that.

Animal hum = new Human("bob", 1);
((Human) hum).talking();

Reason behind is that let's say you have one more class SuperHuman which also extends Animal class and that class doesn't have talking() method then how the compiler would be knowing that reference hum will be referring Human or SuperHuman?

And let's say during initialization you have we have done like Animal hum = new Human("bob", 1); and later in code the hum is updated to hum = SuperHuman("sup", 10);. That's the reason compile time reference is referred and Object is referred at runtime.

答案2

得分: 1

错误是一个编译错误;编译器不关心对象类型实际上是什么(或可能是什么),它只关心它被声明为什么。

另外,我几乎可以肯定你的方法不应该是静态的。

如果你想要做类似于你正在探索的事情,你必须将方法抽象出来,要么作为一个接口,要么作为一个抽象方法。例如:

class abstract Animal {
    abstract void communicate();
}

class Dog extends Animal {
    void communicate() {
        System.out.println("bark");
    }
}

class Human extends Animal {
    void communicate() {
        System.out.println("talk");
    }
}
英文:

The error is a compile error; the compiler doesn’t care what the object type actually is (or could be), it only cares about what it’s declared as.

Also, I’m almost certain your methods should not be static.

If you were to do something like what you’re exploring, you have to abstract out the method, either as an interface or an abstract method. For example:

class abstract Animal {
    abstract void communicate();
}

class Dog extends Animal {
    void communicate() {
        System.out.println("bark");
    }
}

class Human extends Animal {
    void communicate() {
        System.out.println("talk");
    }
}

答案3

得分: 0

以下是您要翻译的内容:

正如Gaurav所说,您必须创建一个对Human的引用或将Animal强制转换为Human。但是,如果Animal是一个接口或抽象类(这不是我特别喜欢做的事情),并且公开了一个所有派生类都必须实现的方法,那么继承可能更合理。

public interface Animal {

    String getName();
    int getAge();
    void blab();
}

public class Human implements Animal {

    private String name;
    private int age;

    Human(String name, int age) {
        this.name = name;
        this.age = age;
    }

    public String getName() { return name; }

    public int getAge() { return age; }

    public void blab() {
        System.out.println("Talk");
    }
}

public class Program {

    public static void main(String[] args) {
        Animal animal = new Human("Bob", 1);
        animal.blab();
    }
}
英文:

As Gaurav says you have to create a reference to Human or cast Animal to Human. But inheritance would make more sense if Animal were an interface or an abstract class (What I don't particularly like to do) and exposed a method in which all derived classes should have to implement.

public interface Animal {

    String getName();
    int getAge();
    void blab();
}

public class Human implements Animal {

    private String name;
    private int age;

    Human(String name, int age) {
        this.name = name;
        this.age = age;
    }

    public String getName() { return name; }
    
    public int getAge() { return age; }

    public void blab() {
        System.out.println("Talk");
    }
}

And the main

public class Program {

    public static void main(String[] args) {
        Animal animal = new Human("Bob", 1);
        animal.blab();
    }
}

huangapple
  • 本文由 发表于 2020年8月14日 12:17:31
  • 转载请务必保留本文链接:https://go.coder-hub.com/63406472.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定