Java: статическое и динамическое связывание (снова)
Я прочитал много блогов, учебных пособий и сотрудничества, но я не понимаю, что такое динамическое связывание в Java. Когда я создаю объект с именем "myspecialcar", он создает объект из класса "car" как тип транспортного средства класса как динамическое связывание, верно? Так что Java знает, что когда я выполняю метод myspecialcar.getType(), у меня есть объект car, и он выполняет метод из класса car. Но почему я получил тип от автомобиля класса? Это потому, что переменная из класса vehicle (тип) является статической привязкой?
С Уважением,
Код:
public class vehicle {
String type = "vehicle";
public String getType(){
return type;
}
}
public class car extends vehicle {
String type = "car";
public String getType(){
return type;
}
}
public class test {
public static void main (String[] args){
vehicle myvehicle = new vehicle(); // static binding
car mycar = new car(); // static binding
vehicle myspecialcar = new car(); //dynamic binding
System.out.println(myspecialcar.getType());
System.out.println(myspecialcar.type);
System.out.println(myspecialcar.getClass());
}
}
Выход:
car
vehicle
class car
4 ответа
Вы не переопределяете переменные класса в Java, вы их скрываете.
Переопределение, например, методы. Сокрытие отличается от переопределения.
В вашем случае вы скрываете переменную-член суперкласса. Но после создания объекта вы можете получить доступ к скрытому члену суперкласса.
Правило метода экземпляра
Когда метод экземпляра вызывается для объекта с использованием ссылки, класс текущего объекта, обозначенный ссылкой, а не тип ссылки, определяет, какая реализация метода будет выполнена.
Свойство экземпляра / Правило поля
Когда к полю объекта обращаются с использованием ссылки, именно тип ссылки, а не класс текущего объекта, обозначенный ссылкой, определяет, к какому полю будет фактически осуществляться доступ.
Вы столкнулись с полями, скрывающимися.
Внутри класса поле с тем же именем, что и поле в суперклассе, скрывает поле суперкласса, даже если их типы различны. Внутри подкласса на поле в суперклассе нельзя ссылаться по его простому имени. Вместо этого поле должно быть доступно через super, что рассматривается в следующем разделе. Вообще говоря, мы не рекомендуем скрывать поля, так как это затрудняет чтение кода.
Есть разница между hiding
а также overriding
, Вы не можете переопределить поля класса, а скорее методы класса. В вашем конкретном примере это означает, что
Vehicle mySpecialCar = new Car() // use upperCase and lowerUpperCase pls
У вас есть тип Vehicle
который является примером Car
, Переопределенные методы будут использоваться, пока поля класса будут скрыты.
Если вы используете
Car myCar = new Car()
ты получишь
myCar.type // car
myCar.super.type // vehicle