加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 编程开发 > Java > 正文

java – 将通用超类强制转换为子类

发布时间:2020-12-15 03:05:38 所属栏目:Java 来源:网络整理
导读:这是我的第一个问题,我希望它对读者和我自己都足够有用!在过去的两天里,我用Google搜索并躲过了这个世界. 我有抽象的模型和存储类,从中派生出具体的模型和存储类: abstract class Food {}abstract class FoodStorageT extends Food { abstract void setFoo
这是我的第一个问题,我希望它对读者和我自己都足够有用!在过去的两天里,我用Google搜索并躲过了这个世界.

我有抽象的模型和存储类,从中派生出具体的模型和存储类:

abstract class Food {}

abstract class FoodStorage<T extends Food> {
    abstract void setFood(T food);
}

class Apple extends Food {}

class Basket extends FoodStorage<Apple> {
    @Override
    void setFood(Apple apple) {
        // Save that apple to the basket
    }
}

没问题.现在,我希望能够直接在Apple实例上调用save(),将其持久化到其篮子中(无需担心篮子),并在抽象类中实现.我发现的最好的是:

abstract class Food<T extends Food<T,S>,S extends FoodStorage<T,S>> {

    abstract S getStorage();

    void save() {
        getStorage().setFood((T)this); // <---- Unchecked cast warning
    }

}

abstract class FoodStorage<T extends Food<T,S>> {
    abstract void setFood(T food);
}

class Apple extends Food<Apple,Basket> {
    Basket basket = new Basket(); // or Basket.getInstance();

    @Override
    Basket getStorage() {
        return basket;
    }
}

class Basket extends FoodStorage<Apple,Basket> {
    @Override
    void setFood(Apple apple) {
        // Save that apple to the basket
    }
}

哪个有效,但IntelliJ给我一个关于save()中未经检查的强制转换的警告.实际上,我是从Food< T,S>对T.

问题:如何以类型安全的方式实现这个apple.save()?

我不希望在客户端代码中出现任何通配符,因此更改抽象void setFood(T food);摘要< Z extends Food< T,S>> void setFood(Z food);不是解决方案. (显然我也在避免SupressWarnings(“未经检查”)).

我知道Java Generics,how to avoid unchecked assignment warning when using class hierarchy?,Generics cast issue和The get-put principle,但我仍然无法理解它.

提前致谢!

解决方法

我认为设计食品与其储存之间存在相互依赖关系,这似乎相当可疑.单向依赖会极大地简化泛型:
class Food { ... }
class FoodStorage<F extends Food> {
    void setFood(F f);
}

但是如果你坚持相互依赖,你可以在没有演员表的情况下做到如下:

abstract class Food<F extends Food<F,S extends FoodStorage<F,S>> {
    abstract F getThis();
    abstract S getStorage();

    void save() {
        getStorage().setFood(getThis());
    }
}
abstract class FoodStorage<F extends Food<F,S>> {
    abstract void setFood(F food);
}

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读