Llamar a un método de subclase desde la superclase
Estoy en un curso de introducción a Java y recién comenzamos a aprender sobre herencia. Estoy trabajando en una tarea que nos pide que creemos una superclase "Mascota" con nombre y edad; y tres subclases, cada una con su propio rasgo único (he elegido "Perro", "Gato" y "Pájaro"). Una vez que hayamos creado todo esto, debemos crear una clase principal para probar todo, y aquí es donde tengo problemas. Estoy intentando llamar a los get
métodos para estos rasgos únicos dentro Main
, pero parece que solo encuentro métodos que están en la superclase.
Aquí está la clase principal:
public class Kennel {
public static void main(String[] args) {
// Create the pet objects
Pet cat = new Cat("Feline", 12, "Orange");
Pet dog = new Dog("Spot", 14, "Dalmation");
Pet bird = new Bird("Feathers", 56, 12);
// Print out the status of the animals
System.out.println("I have a cat named " + cat.getName()
+ ". He is " + cat.getAge() + " years old."
+ " He is " + cat.getColor()
+ "When he speaks he says " + cat.speak());
System.out.println("I also have a dog named " + dog.getName()
+ ". He is " + dog.getAge() + " years old."
+ " He is a " + dog.getBreed()
+ " When he speaks he says " + dog.speak());
System.out.println("And Finally I have a bird named "
+ bird.getName() + ". He is " + bird.getAge() + " years old."
+ " He has a wingspan of " + bird.getWingspan() + " inches."
+ " When he speaks he says " + bird.speak());
}
}
Aqui esta mi superclase
abstract public class Pet {
private String name;
private int age;
// Constructor
public Pet(String petName, int petAge) {
this.name = petName;
this.age = petAge;
}
// Getters
public String getName() { return(this.name); }
public int getAge() { return(this.age); }
// Setters
public void setName(String nameSet) { this.name = nameSet; }
public void setAge(int ageSet) { this.age = ageSet; }
// Other Methods
abstract public String speak();
// toString
@Override
public String toString() {
String answer = "Name: " + this.name + " Age: " + this.age;
return answer;
}
}
Y aquí está una de las subclases (todas tienen el mismo aspecto y tienen el mismo error)
public class Cat extends Pet {
private String color;
// Constructor
public Cat(String petName, int petAge, String petColor) {
super(petName, petAge);
this.color = petColor;
}
// Getters
public String getColor() { return(this.color); }
// Setters
public void setColor(String colorSet) { this.color = colorSet; }
// Other Methods
@Override
public String speak() { return "Meow!"; }
// toString
@Override
public String toString() {
String answer = "Name: " + super.getName() + " Age: "+super.getAge()
+ " Color: " + this.color;
return answer;
}
}
Entonces, lo que sucede es que no puedo hacer que el método principal encuentre el cat.getColor()
método, ni ninguno de los otros exclusivos de las subclases.
Cuando declara que una variable tiene el tipo de superclase, solo puede acceder a métodos (públicos) y variables miembro de la superclase a través de esa variable.
Pet cat = new Cat("Feline",12,"Orange");
cat.getName(); // this is OK
cat.getColor(); // this is not OK, getColor() is not in Pet
Para acceder a los métodos en la clase concreta ( Cat
en este caso), debe declarar la variable como clase derivada
Cat cat = new Cat("Feline",12,"Orange");
cat.getName(); // OK, getName() is part of Cat (and the superclass)
cat.getColor(); // OK, getColor() is part of Cat
O transmítelo a un tipo que sepa/sospeche que es el tipo concreto
Pet cat = new Cat("Feline",12,"Orange");
((Cat)cat).getName(); // OK (same as above)
((Cat)cat).getColor(); // now we are looking at cat through the glass of Cat
Incluso puedes combinar los dos métodos:
Pet pet = new Cat("Feline",12,"Orange");
Cat cat = (Cat)pet;
cat.getName(); // OK
cat.getColor(); // OK
Pet cat = new Cat("Feline",12,"Orange");
^^^
This is the error.
Pet
no tiene un método llamadogetColor()
Necesitas hacer:
Cat cat = new Cat(...);
Cuando haces esto:
Pet cat = new Cat("Feline",12,"Orange");
El compilador ve la variable gato como mascota. Entonces no puedes usar el método específico de la clase Cat.
Tienes que declarar cat como Type Cat para resolver tu problema.
Saludos.
Aquí estás intentando crear un objeto de tipo superclase (cat) usando el constructor (Cat), que es un método de subclase, eso no es posible. esto está violando la regla de herencia.
Pet cat = new Cat("Feline", 12, "Orange");