【问题标题】:Detect Object type then cast it accordingly?检测对象类型然后相应地转换它?
【发布时间】:2010-12-08 01:26:35
【问题描述】:

我的方法将对象作为输入。我如何确定它的类型,然后相应地进行转换?

例如:binarySearch( Object o );

在 binarySearch 方法中,我需要一种方法来确定 Object o 的类型(或类)。然后我需要用那种类型来投射它。我该怎么做???

更具体地说,对象 o 是基类的子类(EG SalariedEmp 是 Employee 的子类),我特别需要基类。

编辑: 我想出了如何做我想做的事,这真的应该是一个完全不同的问题。我需要使用来自Comparable 的 .compareTo 方法来设置一种方法来根据来自这些对象的私有数据比较两个对象。我所要做的就是使用implements 关键字将我的类实现为“Comparable”。因此,无论在我的 binarySearch 方法中比较什么类型的对象,如果它们是相同(未知)类型并且实现了 Comparable,它就可以工作。这使得我的 binarySearch 方法非常适用于任何类型的可比类。

所以,平心而论,我会接受涵盖原始问题的答案。

:)

【问题讨论】:

  • 为什么不让它接受一个员工而不是一个对象?
  • 通常,这是使用 instanceof 运算符完成的,但如果您发布更多代码,我们可能会帮助您找到更好的解决方案,可能会使用泛型,因为它看起来好像您正在处理有一个集合。
  • “我需要...确定类型...”为什么?当您将基类的实例放入同一个容器时,通常会忘记它们的派生类型。您记录了您只关心它们实现基类型接口的事实。
  • @Etienne de Martel 因为我希望它可以广泛用于不同的对象,假设它们是可比的。 @Karl Knechtel 好吧,无论如何,我想通了。我将进入我的方法的所有内容都转换为 Comparable,无论它是什么......所以我假设输入的任何对象都可以与另一个相同类型的对象相媲美......但是如果它们不是相同类型怎么办?跨度>
  • 所以,是的,我只是想创建一个采用 Objects 的方法,以便我可以将它从我的类中取出,并将其放入我的 ToolBox 类中以用于通用目的。示例方法是 BinarySearch、QuickSort 等……所以这些方法适用于各种不同的 Comparable 对象。

标签: java types casting object downcast


【解决方案1】:

两种方法:

  1. 使用instanceof 运算符。

  2. 在对象上调用getClass()(确保首先检查是否为空)。

【讨论】:

    【解决方案2】:
    if (o instanceof SalariedEmp)
        doSomethingWith((SalariedEmp)o);
    

    【讨论】:

      【解决方案3】:

      您可以通过使用 instanceof 运算符或在实例上调用 .getClass() 来使用 RTTI(运行时类型标识),但这几乎总是表明您使用的超类型是错误的超类型-type,或者设计不好。

      在你的情况下,你不需要使用 Object,因为你已经知道你至少有一个 Employee。

      面向对象的范式是你不问对象实例是什么,你要求它做某事。在这种情况下,您可以选择要求 Employee 对象执行的几件事。哪一个是您的最佳选择取决于您要建模的具体内容:

      您可以通过在 Employee 基类中添加一个虚拟方法 boolean isSalaried() 来询问它是否有薪水,然后可能会强制转换它。基本方法会返回 false,但 SalariedEmployee 会覆盖该方法并返回 true。

      但是,虽然这避免了(可能更昂贵的)RTTI,但它并没有避免演员。您可以添加一个方法 SalariedEmployee asSalariedEmployee(),它在基类中将返回 null,而在 SalariedEmployee 中将返回 this。这给了你一个“安全”的演员表,但你仍然需要对 null 进行测试。

      或者您可以只向 Employee 添加一个 Money getSalary() 方法。现在您不必进行任何选角,但您需要确定非受薪员工的薪水是多少;可以是 null、零或 NaN(特殊的 Not a Number 值)。

      如果您决定返回 null,在某些情况下(例如,添加值)您必须针对 null 进行测试,而在其他情况下(例如,将薪水传递给 .equals())则不需要针对 null 进行测试null,因为任何 instance.equals(null) 都应该按照 Object.equals() 的规范返回 false。

      如果你返回零,你可以在不测试 null 的情况下添加,但 equals 可能有点奇怪——两个小时工,每个人都没有工资,有相同的(不存在的)工资,真的是这样吗?这取决于您要建模的内容。如果为真,则返回零。

      如果两个小时工的工资不存在相同,则返回 NaN 值。这只是“空对象模式”的一个特例。

      【讨论】:

      • 您的答案提供了非常好的细节,但 Mike Baranczak 在技术上提供了正确的答案(没有所有好的和信息丰富的材料)。非常感谢您提供的精彩信息。
      猜你喜欢
      • 2013-04-05
      • 1970-01-01
      • 2013-09-27
      • 2015-09-19
      • 2019-12-02
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多