如何从ArrayList中选择特定对象

时间:2016-11-10 07:49:26

标签: java arraylist

我们正在制作一个简单的RPG游戏。现在我们有一个叫做战场的类,玩家可以在那里对抗怪物。当我们开始战斗时,我们使用随机生成器来挑选一个随机怪物。在终端/主要方法中,我们有像" attack"这样的命令。并且"运行",这将对随机怪物造成伤害,或者让玩家离开/退出游戏。现在,我们正在尝试添加一个名为"攻击最可怕的命令",这将让玩家对抗伤害最大的最难的怪物(我们的主要有三个可供选择)。我们需要一种方法来根据损坏从ArrayList怪物中选择一个特定的对象。有没有人有关于我们如何做的提示?

这是我们在Battleground类中启动游戏的代码:

 public void startBattle() {
    printWelcomeMessage();
    boolean finished = false;


    this.currentMonster = getRandomMonster();


    if(this.currentMonster == null) {
        return;
    }

    System.out.println("A random monster is chosen for you. Prepare to meet the mighty " + this.currentMonster.getName());
    System.out.println("\n-------- Player Stats ---------");
    System.out.println(this.player);
    while(!finished && monsters.size() > 0) {
        ArrayList<String> commands = reader.getInput();

        if(isValidCommand(commands)) {

            if(commands.contains("quit") && !this.currentMonster.isDead()){
                System.out.println("You can't quit the game in the middle of a fight!");
            }else if(commands.contains("quit") && this.currentMonster.isDead()) {
                finished = true;
                System.out.println();
                printFinalStats();
                System.out.println();
                System.out.println("You have left the arena, and the game has ended.");
                System.out.println();
            }


            if(commands.contains("run")) {
                finished = true;
                System.out.println("You are a coward and you lose 50 gold pieces...\n");
                this.player.changeGold(-50);
                printFinalStats();
                System.out.println("\nThanks for playing...");

            }else if(commands.contains("drink") && !this.currentMonster.isDead()){
                Potion potion = (Potion) player.findItem(commands.get(1));
                player.drinkPotion(potion);

            }else if(commands.contains("equip") && !this.currentMonster.isDead()){
            Weapons weapon = (Weapons) player.findItem(commands.get(1));
            player.useWeapon(weapon);
            } else if(commands.contains("attack") && !this.currentMonster.isDead()) {

                if(this.player.attack(this.currentMonster)) {
                        playerWon();
                    if(this.monsters.size() > 0) {
                        System.out.println("\nThere are " + this.monsters.size() + " more monsters to beat\nType \"attack\" if you want to attack another monster, or \"quit\" if you want to end the game.");                 
                    } else {
                        System.out.println("\n\n#### Congratulations ####\nYou have beaten every single monster in the game. You are a true champion!");
                        printFinalStats();
                        finished = true;
                    }

                } else if(this.currentMonster.attack(this.player)) {
                    printLosingMessage();
                    finished = true;
                }

            } else if(commands.contains("attack") && this.currentMonster.isDead() && this.monsters.size() > 0) {
                this.currentMonster = getRandomMonster();
                printContinueMessage(this.player, this.currentMonster);
                this.player.changeHealth(50);
            }

        } else {
            System.out.println("Please write a valid command. Valid commands are:");
            printCommands();
        }
    }
}

这是主类中怪物的ArrayList:

 Monster beelzebub = new Monster("Beelzebub", 60);
    Monster witch = new Monster("Witch", 40);
    Monster ogre = new Monster("Ogre", 80);

 ArrayList<Monster> monsters = new ArrayList<>();

    monsters.add(beelzebub);
    monsters.add(witch);
    monsters.add(ogre);

  Battleground battleground = new Battleground(monsters, player, reader);
    battleground.startBattle();

我们感谢任何帮助!

4 个答案:

答案 0 :(得分:1)

将ArrayList替换为SortedSet或PriorityQueue。为Monster类实现Comparator。然后只需选择怪物集合的第一个元素。

答案 1 :(得分:1)

我无法看到你的怪物类,但是我假设构造函数的第二个变量是“伤害等级”&#39;?如果没有,理想情况下这应该属于每个怪物,所以你应该把它放在某个地方。

所以你拥有阵列怪物,它已经拥有了各种级别的怪物。有很多方法你可以做到这一点,但一个简单的方法(假设你只有3个怪物)就是迭代你的怪物并跟踪具有最高伤害的怪物,然后返回那个怪物。

例如:

Monster findHardestMonster(ArrayList<Monster> monsters)
{
   //Set to the first monster in the list ASSUMING you have
   //at least one monster
   Monster highestDamageMonster = monsters.get(0);

   //Go through every monster in your array
   for (Monster monster : monsters)
   {
       //record the highest so far
       if(monster.getDamage() > highestDamageMonster.getDamage())
           highestDamageMonster = monster;
        }
    }

    //return it
    return highestDamageMonster;
}

如果您计划经常移除怪物(例如,当他们被击败时),可能值得作为另一张海报建议使用优先级队列或某种有序收集,其中订购是基于损害级别而不是。然后你不必每次迭代怪物来找到最大伤害的怪物。

答案 2 :(得分:0)

for(int i=0;i<monsters.size()-1;i++){
        Monster m=monsters.get(i);
        Monster m2=monsters.get(i+1); 
        if(m.getDamage()<m2.getDamage()){
            Monster rightMonster=m2;
        }else{
            Monster rightMonster=m;
        }
    }

如果我没有弄错的话,这应该有效。我还没有尝试过代码,但也许它会给你提示

答案 3 :(得分:0)

您可以在列表中执行的流操作可让您轻松完成此操作,方法是max使用Comparator根据损坏对怪物进行排名。

Comparator<Monster> orderByDamage = 
               (m1, m2) -> m1.getDamage() < m2.getDamage() ? -1
                           : m1.getDamage() == m2.getDamage() ? 0 : 1;

这样做可以比较两个怪物(m1m2)的伤害。如果m1的损坏小于m2的损坏,则返回负数。如果它们相等,则返回零,如果m1的伤害大于m2,则返回正数。

注意:如果getDamage()返回Integer而不是int,请将m1.getDamage() == m2.getDamage()替换为Objects.equals(m1.getDamage(), m2.getDamage())

在列表中使用此选项可以获得损害最大的怪物:

Optional<Monster> scariest = monsters.stream().max(orderByDamage);

请注意返回类型,即Optional<Monster>。如果列表不为空,Optional将包含最恐怖的怪物;如果列表为空,则可选将为空 - 如果已删除所有怪物,这将有助于避免NullPointerException

scariest.ifPresent(monster -> /* do something to the monster */);

你也可以使用这种方法来获得伤害最小的怪物:

Optional<Monster> leastScary = monsters.stream().min(orderByDamage);