2

我是新来的,所以我不确定在同一篇文章中是否可以有 2 个问题,所以如果我不应该只告诉我(很好!),我会在这里将其更改为一个问题在别处开始另一个帖子。

第一个问题:

下面的第 5-8 行我指的是两个字符串,我需要比较它们是否相同。我正在使用该getUserInput()方法在终端上从用户那里获得响应,然后我让它继续打印两个字符串,以便我可以直观地检查它们,它们的结果是一样的。但是,if当它们相同时应该运行的部分永远不会运行,然后该else部分总是运行。

第二个问题:

在下面的else部分中,每当currentChump' 的健康状况降低到 时< 1,我都会收到一些我以前从未见过并且不知道该怎么办的异常。

这是我的代码,然后我将在下面粘贴异常:

for (Chump currentChump : chumpArray) {
    System.out.println(" ");
    String playerChoice = helper.getUserInput(
                          "Type the name of the Weapon that you wish to use.");
    System.out.println(playerChoice);
    System.out.println(currentChump.getWeakness().toLowerCase());
    if (currentChump.getWeakness().toLowerCase() == playerChoice) {
        chumpArray.remove(currentChump);
    } // END IF
    else {
        while (PlayerIsAlive && currentChump.getHealth() > 0) {
            int damage = (int) Math.floor((Math.random() * 6) + 1);
            System.out.println(currentChump.getName() + " has "
                             + currentChump.getHealth() + "health remaining.");
            currentChump.setHealth(currentChump.getHealth() - damage);
            System.out.println("You hit the enemy for " 
                             + damage + " points of damage.");
            System.out.println(currentChump.getName() + " has " 
                             + currentChump.getHealth() + " health remaining.");
    System.out.println(" ");
            if (currentChump.getHealth() < 1) {
                chumpArray.remove(currentChump);
            } // END IF
            else {
                int damage2 = (int) Math.floor((Math.random() * 4) + 1);
                player.setHealth(player.getHealth() - damage2);
                if (player.getHealth() < 1) {
                    PlayerIsAlive = false;
                } // END IF
            } // END WHILE
        } // END ELSE
    } // END ELSE
} // END FOR

例外:

Exception in thread "main" java.util.ConcurrentModificationException
at java.util.AbstractList$Itr.checkForComodification(AbstractList.java:372)
at java.util.AbstractList$Itr.next(AbstractList.java:343)
at ArenaGameCopy.startPlaying(ArenaGameCopy.java:87)
at ArenaGameCopy.main(ArenaGameCopy.java:168)
4

3 回答 3

7

您不能使用 == 来比较字符串,因为 == 将比较对象......而不是字符串的值

if (currentChump.getWeakness().toLowerCase() == playerChoice)

应该

if (currentChump.getWeakness().toLowerCase().equals(playerChoice))

或者

 if (currentChump.getWeakness().equalsIgnoreCase(playerChoice))

第二个问题似乎您正在尝试修改属于另一个线程的对象(您的列表)。

于 2013-07-28T03:07:59.093 回答
7

Iterator当您想从列表中删除项目并使用 Iterator.remove() 而不是修改底层列表时,用于循环进入

引用JavaDoc

...通常不允许一个线程在另一个线程对其进行迭代时修改 Collection。一般来说,在这些情况下,迭代的结果是不确定的。如果检测到此行为,某些迭代器实现(包括 JRE 提供的所有通用集合实现的那些)可能会选择抛出此异常。这样做的迭代器被称为快速失败迭代器,因为它们快速而干净地失败,而不是在未来不确定的时间冒着任意的、非确定性的行为的风险。

请注意,此异常并不总是表示对象已被不同的线程同时修改。如果单个线程发出一系列违反对象约定的方法调用,则该对象可能会抛出此异常。例如,如果线程在使用快速失败迭代器迭代集合时直接修改了集合,则迭代器将抛出此异常。

请注意,不能保证快速失败的行为,因为一般来说,在存在不同步的并发修改的情况下,不可能做出任何硬保证。快速失败操作会尽最大努力抛出 ConcurrentModificationException。因此,编写一个依赖此异常来确保其正确性的程序是错误的:ConcurrentModificationException 应该仅用于检测错误。


让我来帮助你。阅读代码中的注释:

import java.util.*;

/**
  Hello! Welcome to basics.
  This is what called a SSCCE.
  Next time anyone asks for it, do it.
  Because, 90% of the times, creating SSCCE will help you identify the issue.
  Hope you learn something from these lines.

  To compile and execute this code do the following:
  a. Paste this class from import to last closed bracket in a 
     file named Test.java
  b. javac Test.java
  c. java Test
  Bliss!
*/
public class Test{

  public static void main(String[] args){
    // 1. Do not worry about these lines
    //    I am just creating some sample data
    List<String> chumpArray = Arrays.asList("Oh my god! You must know to create SSCCE".split("\\s"));
    chumpArray = new ArrayList<String>(chumpArray);
    System.out.println("List to be iterated: " + chumpArray);

    // 2. This is what I meant when I said to use an Iterator
    //    Obviously, your iterator will look like Iterator<Chump>
    for(Iterator<String> chumpIt = chumpArray.iterator(); chumpIt.hasNext();) {

        // 3. Materialize the current item
        String currentChump = chumpIt.next();
        System.out.println("Currently on: " + currentChump);

        // 3. String comparison
        //    ==            WRONG
        //    .equals       RIGHT
        if (currentChump.toLowerCase().equals("you")) {
          System.out.println("DELETING: " + currentChump);
          // 4. Just ask the iterator to remove the current Item
          chumpIt.remove();
          // Was it really so hard?!
        }
    }
    System.out.println("List after delete: " + chumpArray);
  }
}

在执行此操作时,我们得到

tmp$ java Test
List to be iterated: [Oh, my, god!, You, must, know, to, create, SSCCE]
Currently on: Oh
Currently on: my
Currently on: god!
Currently on: You
DELETING: You
Currently on: must
Currently on: know
Currently on: to
Currently on: create
Currently on: SSCCE
List after delete: [Oh, my, god!, must, know, to, create, SSCCE]

HTH
尼山特

于 2013-07-28T03:00:25.597 回答
4

第一个问题

比较字符串时始终使用equals !

操作员所做的==是检查对象是否相同。

这似乎与 Strings 一起工作的唯一原因是因为叫做interning

这意味着,除非明确使用了 String 构造函数,否则具有相同字符序列的引用指向相同的 String 对象。这是为了减少内存使用量。

第二个问题

Exception in thread "main" java.util.ConcurrentModificationException

这是由使用增强的 for 循环修改您正在迭代的结构引起的。

链接解释了抛出异常的原因。

在迭代器的每个 next() 方法调用中,

  final void checkForComodification() {
      if (modCount != expectedModCount)
    throw new ConcurrentModificationException();
  }

方法被调用,以检查列表中是否有机会。如果它们不匹配,这将引发 ConcurrentModificationException。

附加评论

为了您似乎部分尊重的约定,您可以将布尔变量从重命名为PlayerIsAliveto isPlayerAlive。这是在骆驼情况下,带有第一个小写字母和一个“是”,以立即向读者表明它是一个真/假值。

于 2013-07-28T03:35:42.950 回答