Java 方法重写返回null
我是Java的新手。所以这个问题听起来可能很简单,但我被卡住了,无法理解为什么这段代码返回null和0.0 文件:Transport.java public class Transport { private String name; private double price; public Transport(String name, double price) { this.name = name; this.price = price; } public String carName() { return name; } public double carPrice(){ return price; } } 公共交通{ 私有字符串名称; 私人双价; 公共交通(字符串名称,双倍价格){ this.name=名称; 这个价格=价格; } 公共字符串carName(){ 返回名称; } 公共双卡普里斯(){ 退货价格; } } 文件:Car.java public class Car extends Transport{ protected String name; protected double price; public Car(String name, double price) { super(name, price); } @Override public String carName(){ return name; } @Override public double carPrice(){ return price * 1.5; } } 公车扩展交通{ 受保护的字符串名称; 保护双重价格; 公共汽车(字符串名称,双倍价格){ 超级(名称、价格); } @凌驾 公共字符串carName(){ 返回名称; } @凌驾 公共双卡普里斯(){ 退货价格*1.5; } } 文件:Main.java public class Main { public static void main(String[] args) { Car c = new Car("CarBrand", 1000); System.out.println("Name: " + c.carName()); System.out.println("Price: " + c.carPrice()); } } 公共班机{ 公共静态void main(字符串[]args){ c车=新车(“卡伯兰”,1000); System.out.println(“名称:+c.carName()); System.out.println(“价格:+c.carPrice()); } } 输出 Name: null Price: 0.0 名称:空 Price:0.0您在Java 方法重写返回null,java,overriding,Java,Overriding,我是Java的新手。所以这个问题听起来可能很简单,但我被卡住了,无法理解为什么这段代码返回null和0.0 文件:Transport.java public class Transport { private String name; private double price; public Transport(String name, double price) { this.name = name; this.pri
Car
中声明了单独的name
和Price
变量,并且从未给它们赋值-它们与Transport
中声明(并初始化)的name
和Price
变量不同。基本上,您可以看到String
和double
的默认值。去掉汽车中的那些额外变量
,并使用super.carPrice()
从运输
获取原始价格:
public class Car extends Transport {
public Car(String name, double price) {
super(name, price);
}
@Override
public double carPrice(){
return super.carPrice() * 1.5;
}
}
请注意,根本不需要重写carName()
,除非您确实希望它改变行为
我还建议将
carName()
和carPrice()
更改为getName()
和getPrice()
,使其更为地道。问题是name
有两个不同的变量,一个在车内,一个在运输中c.carName()
返回未初始化的Car.name
如果你的汽车等级是下面的那一级,它就可以工作了
public class Car extends Transport {
public Car(String name, double price) {
super(name, price);
}
@Override
public double carPrice(){
return price * 1.5;
}
}
变量
price也是如此,派生类Car
隐藏了类Transport
的实例变量。因此,尽管您从Transport
类继承了正确初始化的数据成员,但是初始化为默认值的Car
类实例变量将从Car
类方法返回您正在通过super()将这两个值传递给父类传输。所以
终将定局
传输类属性名称和价格
您不需要在Car类中声明这两个属性。Car将通过继承隐式地具有这两个属性。这里您正在为Car创建单独的属性。当您创建Car类型的“c”对象时,您只为类Transport的“name”和“price”变量赋值(因为在构造函数中您调用super(name,price),它将从父类调用构造函数)
这里:c.carName()从Car类调用该方法(因为它被标记为@Override),这个方法从Car类返回'name'变量的值。在你的例子中,这个变量是空的,因为你还没有给它赋值。
您为Transport类型的'name'变量指定了值“CarBrand”。
“price”变量也是如此。使用super将通过调用构造函数super(名称、价格)返回已存储在父类中的值,使用super后跟点表示法将访问父类方法。因此super.carPrice()将返回存储在父类中的值
此外,@Override注释只应用于更改父类中的现有方法,在子类中使用新功能,而不更改名称。因此,对于@Overide for carname(),您需要调用super.carname(),因为您正在从父类返回值
简言之,之所以会得到null和0.0,是因为在应该访问父类值时,您正在访问子类值
public class Car extends Transport{
protected String name;
protected double price;
public Car(String name, double price) {
super(name, price);
}
@Override
public String carName(){
return name;
}
@Override
public double carPrice(){
return price * 1.5;
}
}
Your class should be
public class Car extends Transport{
public Car(String name, double price) {
super(name, price);
}
public String getName(){
return super.carName();
}
@Override
public double carPrice(){
return super.carPrice()* 1.5;
}
}
你的主课现在应该是
public class Main {
public static void main(String[] args) {
Car c = new Car("CarBrand", 1000);
System.out.println("Name: " + c.getName());
System.out.println("Price: " + c.carPrice());
}
}
好的,明白了。但是,从Car
类调用方法carPrice()
的正确方法是什么呢?@Gerardas:我不知道你的意思。我在回答中向您展示了如何从Car
调用Transport
实现来调用原始方法,该方法只返回price
变量。。。使用我答案中的代码替换你的类,这就是你所需要做的。当你写评论时,上面没有代码。。。谢谢你的帮助!:)@Gerardas调用继承的方法的正确方法是:c.carPrice()-如果它在您的上下文中可见(取决于它是公共的、包私有的、受保护的),它就会像您在Car中声明的一样出现。此更正会导致错误:线程“main”中出现异常java.lang.Error:未解决的编译问题:Transport.price字段不可见
如果您的类名为“Car”,通常不需要在属性名称中添加“Car”。您可能还希望尽早习惯重要的bean模式,并通过“get”和“set”前缀属性访问器。考虑这样的名字:Car MyCar=新车(…)、MyCar、GETNAME()
public class Main {
public static void main(String[] args) {
Car c = new Car("CarBrand", 1000);
System.out.println("Name: " + c.getName());
System.out.println("Price: " + c.carPrice());
}
}