我正在进行一场扑克游戏,我试图测试并看看是否有任何玩家手中有皇家同花顺。然而,在我测试之前,我遇到了一个障碍:我没有一种快速而简单的方法来测试每个玩家的手牌,包括Ace,King,Queen,Jack和10个西装。 到目前为止,这是我的代码:
private void findWinner() {
// p1 hand
List<String> p1hand = cards.subList(10, 15);
p1hand.addAll(cards.subList(0, 2));
System.out.println("Player 1's total hand is " + p1hand);
// p1 hand
List<String> p2hand = cards.subList(10, 15);
p2hand.addAll(cards.subList(2, 4));
System.out.println("Player 2's total hand is " + p2hand);
// testing for royal flush
String[] spadeRoyalFlush = {"Ace of spades", "King of spades", "Queen of spades", "Jack of spades", "10 of spades"};
String[] heartRoyalFlush = {"Ace of hearts", "King of hearts", "Queen of hearts", "Jack of hearts", "10 of hearts"};
String[] dimRoyalFlush = {"Ace of diamonds", "King of diamonds", "Queen of diamonds", "Jack of diamonds", "10 of diamonds"};
String[] clubRoyalFlush = {"Ace of clubs", "King of clubs", "Queen of clubs", "Jack of clubs", "10 of clubs"};
// p1
boolean p1royalFlush = false;
if(p1hand.contains(spadeRoyalFlush)) { // line 104
p1royalFlush = true;
}
if(p1hand.contains(heartRoyalFlush)) {
p1royalFlush = true;
}
if(p1hand.contains(dimRoyalFlush)) {
p1royalFlush = true;
}
if(p1hand.contains(clubRoyalFlush)) {
p1royalFlush = true;
}
if(p1royalFlush) {
System.out.println("Player 1 got a royal flush with " + p1hand);
}
// p2
boolean p2royalFlush = false;
for(int i=0; i<p2hand.size(); i++) {
if(p2hand.contains(spadeRoyalFlush)) {
p2royalFlush = true;
}
if(p2hand.contains(heartRoyalFlush)) {
p2royalFlush = true;
}
if(p2hand.contains(dimRoyalFlush)) {
p2royalFlush = true;
}
if(p2hand.contains(clubRoyalFlush)) {
p2royalFlush = true;
}
}
if(p2royalFlush) {
System.out.println("Player 2 got a royal flush with " + p2hand);
}
} // line 165 is where I call this method
cards
是一个字符串数组列表,其中包含每张卡片的每个名称(例如“黑桃王牌”,“心中的3张”等)
当我运行此代码时,我收到错误:
Exception in thread "main" java.util.ConcurrentModificationException
at java.base/java.util.ArrayList$SubList.checkForComodification(Unknown Source)
at java.base/java.util.ArrayList$SubList.listIterator(Unknown Source)
at java.base/java.util.AbstractList.listIterator(Unknown Source)
at java.base/java.util.ArrayList$SubList.iterator(Unknown Source)
at java.base/java.util.AbstractCollection.contains(Unknown Source)
at poker.PlayGame.findWinner(PlayGame.java:104)
at poker.PlayGame.doEverything(PlayGame.java:165)
at poker.MainPoker.main(MainPoker.java:7)
我研究了这意味着什么,我感到震惊,因为据我所知,我没有在我的代码中迭代任何东西。
这是DoEverything方法:
public void doEverything() {
dealHands();
throwCards();
findWinner(); // line 165
}
这是主要方法:
public static void main(String[] args) {
PlayGame game = new PlayGame();
game.doEverything(); // line 7
}
答案 0 :(得分:5)
我会使用List.containsAll()
作为记录here。
如果此列表包含指定集合的所有元素,则返回true。
String[] array = ...;
List<String> list = ....;
list.containsAll(Arrays.asList(array));
重新点击第104行的ConcurrentModificationException
,您在contains()
上呼叫p1hand
,但p1hand
来自cards.subList(10, 15)
。
我们无法看到cards
来自哪里。您尚未发布必要的代码来调试该点。但请参阅@devpuh的答案,了解有关在子列表上调用contains()
的更多详细信息。
答案 1 :(得分:1)
小心List.subList(int fromIndex, int toIndex)
!
返回指定fromIndex(包含)和toIndex(独占)之间此列表部分的视图。 (如果fromIndex和toIndex相等,则返回的列表为空。)返回的列表由此列表支持,因此返回列表中的非结构更改将反映在此列表中,反之亦然。返回的列表支持此列表支持的所有可选列表操作。
(...)
如果支持列表(即此列表)在结构上以除返回列表之外的任何方式进行修改,则此方法返回的列表的语义将变为未定义。 (结构修改是那些改变了这个列表的大小,或以其他方式扰乱它的方式,正在进行的迭代可能会产生不正确的结果。)
此创建列表上的所有更改都将影响原始列表!
当您尝试访问原始列表结构更改时的子列表时,您会得到ConcurrentModificationException
。 (在您的情况下,您向列表cards
添加了一个新元素)
更改
List<String> p1hand = cards.subList(10, 15);
p1hand.addAll(cards.subList(0, 2));
到
List<String> p1hand = new ArrayList<>(cards.subList(10, 15)); // create a new list
p1hand.addAll(cards.subList(0, 2));
并检查列表是否包含所有特定卡片使用
p1hand.containsAll(Arrays.asList(spadeRoyalFlush));