在面向对象编程中,总是向下转换变量是否安全?
In object oriented programming, is it safe to always downcast a variable?
这更多是关于编译器理论,因为我正在尝试制作一个。我想知道在子类中总是向下转型变量在理论上是否安全。
class Car {
BodyType myBodyType;
}
class Corvette extends Car {
FourWheels myBodyType;
// normally this is rejected by most compilers
// redefinition of myBodyType;
}
class BodyType {}
class FourWheels extends BodyType {}
目前在传统的 OO 编程中,如果我们知道 myBodyType 始终是特定类型,我们总是必须将 myBodyType 向下转换为 FourWheels。如果这由编译器自动完成,是否安全?
不,这不安全,因为现在没有什么能阻止用户写:
Car car = new Corvette();
car.myBodyType = new TwoWheels();
现在将 car
中的 myBodyType
向下转换为 FourWheels
类型可能会导致有问题的行为。
您可以依赖 myBodyType
永远不会是错误类型的唯一方法是保证永远不会将错误类型的值写入其中 - 例如通过将其设置为在构造期间设置的只读值。
顺便说一下,在类似 Java 的语言中,用户更优雅的方法是:
class Car<MyBodyType extends BodyType> {
MyBodyType myBodyType;
}
class Corvette extends Car<FourWheels> {
...
}
这更多是关于编译器理论,因为我正在尝试制作一个。我想知道在子类中总是向下转型变量在理论上是否安全。
class Car {
BodyType myBodyType;
}
class Corvette extends Car {
FourWheels myBodyType;
// normally this is rejected by most compilers
// redefinition of myBodyType;
}
class BodyType {}
class FourWheels extends BodyType {}
目前在传统的 OO 编程中,如果我们知道 myBodyType 始终是特定类型,我们总是必须将 myBodyType 向下转换为 FourWheels。如果这由编译器自动完成,是否安全?
不,这不安全,因为现在没有什么能阻止用户写:
Car car = new Corvette();
car.myBodyType = new TwoWheels();
现在将 car
中的 myBodyType
向下转换为 FourWheels
类型可能会导致有问题的行为。
您可以依赖 myBodyType
永远不会是错误类型的唯一方法是保证永远不会将错误类型的值写入其中 - 例如通过将其设置为在构造期间设置的只读值。
顺便说一下,在类似 Java 的语言中,用户更优雅的方法是:
class Car<MyBodyType extends BodyType> {
MyBodyType myBodyType;
}
class Corvette extends Car<FourWheels> {
...
}