Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/oop/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/silverlight/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 类层次结构和设置_Java_Oop - Fatal编程技术网

Java 类层次结构和设置

Java 类层次结构和设置,java,oop,Java,Oop,因此,我正在尝试制作一个简单的RPG类文本游戏,以巩固我的一些研究成果,我想知道实现这种设置的最佳方法是: 名为Fighter>的接口由AbstractFighter>MagicFighter和StrengthFighter扩展AbstractFighter实现。(最初MagicFighter和StrengthFighter有自己的接口,具有其他独特的行为)但是 现在让人困惑的是,我希望玩家能够在这两种类型的战斗机中进行选择,然后将其存储在列表(战斗机)中。所以很明显,我得到的类型总是Fight

因此,我正在尝试制作一个简单的RPG类文本游戏,以巩固我的一些研究成果,我想知道实现这种设置的最佳方法是:

名为Fighter>的接口由AbstractFighter>MagicFighter和StrengthFighter扩展AbstractFighter实现。(最初MagicFighter和StrengthFighter有自己的接口,具有其他独特的行为)但是

现在让人困惑的是,我希望玩家能够在这两种类型的战斗机中进行选择,然后将其存储在列表(战斗机)中。所以很明显,我得到的类型总是Fighter(必须是因为我不知道用户将选择哪个Fighter实现),我只能调用Fighter接口中的方法

我可以做的一件事是,每次我需要调用不同战斗机实现特有的方法时,都要检查玩家选择了什么,并进行向下转换。但这将意味着大量重复的代码,而且听起来很混乱=/

另一种可能是运行检查并根据用户的选择将用户添加到列表(StengthFighter)或列表(MagicFighter),但最终这与之前的“解决方案”问题完全相同

我能想到的最后一件事是尝试和镜像Fighter的每个实现,以便每个实现总是有一个版本的每个行为。比如说 无效再生();在战斗机界面中,然后对StrengthFighter和MagicFighter执行不同的操作(魔法战斗机可能会恢复法力,力量战斗机可能会在每次使用攻击时恢复怒气()(这是另一个问题,因为魔法战斗机需要执行恢复(),这显然是公开的,但在StrengthFighter中使用它是私人的)

不管怎么说,你现在可能已经明白要点了,所以我不会再发短信了


归根结底,这是我实现中的一个缺陷,还是OO编程不可避免?我的意思是,归根结底,Java如何知道结果需要什么类型(并因此使用它的方法)如果它要求用户做出决定以确定类型。

这是一个基于对您的问题的解释的粗糙类实现。您最初定义的是一个接口,然后是一个实现,然后是单个类型,这感觉很复杂。相反,我们希望使用单个
战斗机
s,而不是r他们的代表

class Fighter {
    int hp;

    void attack() {

    }

    void move() {

    }

    void regen() {
        hp++;
    }
}

class MagicFighter extends Fighter {
    int mana;

    @Override
    void regen() {
        mana++;
        //we don't regen hp because we're magic-type.
    }
}

class StrengthFighter extends Fighter {
    int rage;

    @Override
    void attack() {
        super.attack();
        specialRegen();
    }

    void specialRegen() {
        rage++;
    }

    @Override
    void regen() {
        // does nothing
    }

    void berserk() {
        rage--;
    }
}
在这种情况下,我们可以存储
战斗机的列表

List<Fighter> fighters = new List<>();
然后,我们将正常调用所有方法。这两个类之间共享的任何方法都不会被重写,例如
Fighter.move
。对于一种类型无效的任何方法都会被重写,例如
StrengthFighter.regen
。对于特定类型具有特殊附加功能的任何方法都将实现addit然后打一个
super
电话,比如
StrengthFighter.attack

基本上,您已经有了正确的想法,但基本上,您希望
战斗机
尽可能多地执行共享工作,然后根据幕后的类型执行单独的操作。如果需要检查某个类型,则它需要是该类型战斗机特有的,例如
StrengthFighter.berserk


这就减少了检查类型的需要,除非它们真的很重要。

我认为你有唯一的战斗机>FighterImpl。其他人员应该单独执行:武器、装甲、能力等

在创造时,你授予战士能力+武器(受能力限制)+额外津贴。然后所有战士生活在相同的条件下

interface Fighter {
    int getSpeed(); // base fighter speed per time unit
    Armor getArmor(); 
    Weapon getWeapon(); 
    Damage attack(Fighter enemy); // animate + apply damage
    Position move();
    List<Perks> getPerks();
    List<Ability> getAbilities();
}

interface Weapon {
    DamageType getDamageType();
    int getDamage();
    void animateHit(Fighter enemy);
}

abstract class AbstractWeapon implements Weapon {
    ...
}

abstract class MeleeWeapon extends AbstractWeapon {
    ...
}

abstract class MagicWeapon extends AbstractWeapon {
    ...
}
接口战斗机{
int getSpeed();//每时间单位的基本战斗机速度
防弹衣();
武器获取武器();
伤害攻击(战斗机敌人);//动画+施加伤害
位置移动();
列出getPerks();
列出getAbilities();
}
接口武器{
DamageType getDamageType();
int getDamage();
敌方战斗机;
}
抽象类AbstractWearm实现武器{
...
}
抽象类MeleeWearm扩展了AbstractWearm{
...
}
抽象类MagicWeapon扩展了AbstractAnswarm{
...
}

让Fighter拥有一个公共类,该类的功能类似于样板文件Fighter,并扩展/覆盖MagicFighter和StrengthFighter特定的方法。另一种选择是只创建一个Fighter类,根据枚举类型处理所有事情。OO很好,但当它变得像您所展示的那样混乱时,请删除一些复杂性并保持简单。当用户选择其类型时,只需调用new MagicFighter(),然后它就会自然地调用特定方法?嘿,谢谢你花时间查看我的问题并提供答案。因此,最终调用berserk()例如,我需要沮丧,但只有在真正需要的时候?@FinalFind yes。如果一个普通的
战斗机
不知道狂暴,你就不能真的调用它。当然,你也可以编写一个名为
特殊性
的方法,但问题是你不知道这个特殊能力是否适用,所以最后,隐藏了一个事实你想叫狂暴帮不了忙。
interface Fighter {
    int getSpeed(); // base fighter speed per time unit
    Armor getArmor(); 
    Weapon getWeapon(); 
    Damage attack(Fighter enemy); // animate + apply damage
    Position move();
    List<Perks> getPerks();
    List<Ability> getAbilities();
}

interface Weapon {
    DamageType getDamageType();
    int getDamage();
    void animateHit(Fighter enemy);
}

abstract class AbstractWeapon implements Weapon {
    ...
}

abstract class MeleeWeapon extends AbstractWeapon {
    ...
}

abstract class MagicWeapon extends AbstractWeapon {
    ...
}