【问题标题】:Cast List<Son> to List<Father>演员表<儿子>到列表<父亲>
【发布时间】:2013-02-27 12:10:28
【问题描述】:

我有一个名为“Father”的简单 POJO 和另一个名为“Son”的 POJO,它扩展了“Father”,这是最简单的类继承示例。

现在我有一个List&lt;Son&gt;,我需要将它转换为List&lt;Father&gt;

我该怎么办?

编辑

抱歉命名不好,我没有解释自己。 PersonEmployee 会是一个更好的例子。或者产品计算机

【问题讨论】:

  • 你为什么要投“下”? SonFather,所以它可以做任何 Father 可以做的事情...
  • You can't => 您需要复制内容。
  • 这里有一个逻辑缺陷。不是每个Son 都是Father。然而,在平行宇宙中它可能是真的。
  • SonFather?一个儿子有一个父亲。现实世界的例子呼吁组合而不是继承!
  • 面向对象编程中的继承与生物学中的含义完全不同。在 OO 中,继承意味着专业化:子类是超类的专业​​化版本。为类使用诸如FatherSon 之类的名称会使它与继承的生物学意义相混淆。

标签: java list collections casting


【解决方案1】:

2 条建议:

有一个接口,比如PersonFather(因此是Son)实现的。两者都使用List&lt;Person&gt;

使用集合构造函数创建一个new List&lt;Father&gt;,例如List&lt;Father&gt; fathers = new ArrayList&lt;Father&gt;(sons);

【讨论】:

    【解决方案2】:

    暂时假设您可以通过演员表做到这一点,这将导致以下问题:

    List<Son> ls = ...;
    List<Father> lf = (List<Son>) ls;
    lf.add(new Father());
    

    lslf 都指向同一个实例,因此您刚刚将 Father 对象添加到 Sons 列表中。

    【讨论】:

      【解决方案3】:

      如上所述,您不能在此处使用演员表*。您可以编写一个小的帮助方法来进行转换(即复制):

      private static List<Father> getListFather(List<? extends Father> list) {
          return new ArrayList<> (list);
      }
      

      * 实际上你可以 - 参考另一个答案:List&lt;Father&gt; listFather = (List&lt;Father&gt;) (List&lt;? extends Father&gt;) listSons;

      【讨论】:

      • 这段代码错过了方法签名中的&lt;A&gt;,仍然需要使用通用提示调用,但这是我知道的唯一类型安全的方式。
      • @Slanec 你是什么意思“这个代码错过了方法签名中的 ”? (我把A改成了Father,其他都一样)
      • 使用Father 效果很好。我认为您的 A 是该方法的通用类型,可以处理所有可能的类型。在这种情况下,它需要是private static &lt;A&gt; List&lt;A&gt; getList(List&lt;? extends A&gt; list),并且在调用时还需要一个通用提示。
      【解决方案4】:

      这似乎有效:

      static class Father {};
      static class Son extends Father{};
      
      public void test() {
        List<Son> sons = new ArrayList<>();
        // Not allowed.
        //List<Father> sons2 = (List<Father>)sons;
        // Two step.
        List<? extends Father> sons3 = sons;
        List<Father> sons4 = (List<Father>)sons3;
        // Direct.
        List<Father> sons5 = (List<Father>)((List<? extends Father>)sons);
      }
      

      【讨论】:

      • 另外,List&lt;Father&gt; fathers = (List&lt;Father&gt;)(List&lt;? super Son&gt;)sons;。但请注意,您正在避免 Java 类型安全,这可能会很容易适得其反!
      • 不确定我会推荐它,但很好 ;-)
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2013-03-14
      • 2017-12-02
      • 1970-01-01
      • 1970-01-01
      • 2015-05-06
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多