-2

So I am working on a poker game and have completed my straight and pair hands but have no idea where to start on my 3 of a kind. Any help would be apprciated here is my poker hand package. If I can get the three of a kind hand done I can finally move on to the rest so this hand has got me stuck completely.

package edu.rcc.hand;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;

import edu.rcc.deck.Card;

public class Hand implements Comparable<Object> {

//Card[] theCards = new Card[10];
private ArrayList<Card> theCards = new ArrayList<Card>();

public Hand(ArrayList<Card> theCards) {
    this.theCards = theCards;
}

public String toString() {
    String s = "";
    for (Card c : theCards) {
        s += c.toString() + ", ";
    }
    return s;
}

private ArrayList<Card> getHandInNumericalOrder() {
    ArrayList<Card> sorted = new ArrayList<Card>();
    sorted.addAll(this.theCards);
    Collections.sort(sorted, new Comparator<Card>() {

        @Override
        public int compare(Card o1, Card o2) {
            Integer o1Value = o1.getNumericalValue();
            Integer o2Value = o2.getNumericalValue();
            return o1Value.compareTo(o2Value);

        }

    });
    return sorted;
}

/**
 * a method to get cards that have the same value
 */
private boolean isPair(ArrayList<Card> sortedCards) {

    Card previousCard = null;
    for (Card c : sortedCards) {

        if (previousCard != null && previousCard.isSameFace(c)) {
            return true;
        } else {
            previousCard = c;
        }


    }
    return false;
}


private boolean ThreeOfKind(ArrayList<Card> sortedCards)
 {

    Card previousCard = null;
    for (Card c : sortedCards) {


        if (previousCard != null && previousCard.isSameFace(c) ) {
            return true;
        } else {
            previousCard = c;
        }


    }
    return false;
}

/**
 * if the sum of the integer array is equal to the following:
 * 1 - 
 * @return
 */
private ArrayList<Integer> numberOfSameCards() {
    ArrayList<Card> sortedCards = this.getHandInNumericalOrder();

    ArrayList<Integer> cardCounts = new ArrayList<Integer>();
    int numbSame = 1;
    for (int i = 0; i < sortedCards.size() - 1; ++i ) {
        if (sortedCards.get(i).isSameFace(sortedCards.get(i+1))) {
            ++numbSame;
        } else {
            for (int j = 0; j < numbSame; ++j) {
                cardCounts.add(numbSame);
            }
            numbSame = 1;
        }
    }
    for (int i = 0; i < numbSame; ++i) {
        cardCounts.add(numbSame);
    }


    return cardCounts;
}

/**
 * 5 - high card || strait || strait flush || flush
 * 7 - pair
 * 9 - 2 pair
 * 11 - 3 of a kind
 * 13 - full house
 * 17 - four of a kind
 * @param inputArray
 * @return
 */
private int getSum(ArrayList<Integer> inputArray) {
    int sum = 0;
    for (int i : inputArray) {
        sum += i;
    }
    return sum;
}

/**
 * 0 - high card
 * 1 - pair
 * 2 - 2 pair
 * 3 - three of a kind
 * 4 - strait
 * 5 - flush
 * 6 - full house
 * 7 - four of a kind
 * 8 - strait flush
 * @return
 */
private int getRank() {
    ArrayList<Card> sorted = this.getHandInNumericalOrder();
    int rawSum = getSum(numberOfSameCards());
    switch (rawSum) {
        case 7:
            return 1;
        case 9:
            return 2;
        case 11:
            return 3;
        case 13:
            return 6;
        case 17:
            return 7;
        default:
            //TODO CHECK FOR ALL OTHER HAND TYPES
    }
    boolean isFlush = isFlush(sorted);
    boolean isStrait = isStrait(sorted);
    if (isFlush && isStrait) {
        return 8;
    } else if (isFlush) {
        return 5;
    } else if (isStrait) {
        return 4;
    } else {
        return 0;
    }
}

private boolean isFlush(ArrayList<Card> theCards) {

    for (int i = 0; i < theCards.size() - 1; i++) {
        if (!theCards.get(i).isSameSuit(theCards.get(i + 1))) {
            return false;
        }
    }
    return true;

}

/**
 * 
 * @param sortedCards - all have unique faces
 * @return
 */
private boolean isStrait(ArrayList<Card> sortedCards) {

    for (int i = 0; i < theCards.size(); i++) {

        int current = theCards.get(i).getNumericalValue();

        int next = theCards.get(i + 1).getNumericalValue();

        if (current + 1 == next || 
                (current == 5 && next == 14)) {
            continue;
        } else {
            return false;
        }

    }
    return true;

}

/**
 * 0 -> equal
 * 1 -> this > o
 * -1 -> this < o
 */
@Override
public int compareTo(Object o) {
    if (!(o instanceof Hand)) {
        return 1;
    }
    Hand other = (Hand)o;


    boolean isThisPair = other.isPair(other.getHandInNumericalOrder());
    boolean isThisPair2 = this.isPair(this.getHandInNumericalOrder());
    boolean isStrait = this.isStrait(this.getHandInNumericalOrder());
    boolean isStrait2 = other.isStrait(other.getHandInNumericalOrder());
    boolean isFlush = this.isFlush(this.getHandInNumericalOrder());
    boolean isFlush2 = other.isFlush(other.getHandInNumericalOrder());
    boolean ThreeOfKind = this.isFlush(this.getHandInNumericalOrder());
    boolean ThreeOfKind2 = other.isFlush(other.getHandInNumericalOrder());

    ArrayList<Card> otherNumerical = other.getHandInNumericalOrder();
    ArrayList<Card> thisNumerical = this.getHandInNumericalOrder();


    System.out.println(thisNumerical);
    System.out.println(otherNumerical);


    if(isThisPair2 == true)
    {
        System.out.println("The first hand is a pair");
    }
    if(isThisPair == true){
        System.out.println("The second hand has a pair");
    }
    if (isStrait == true){
        System.out.println("The first hand has a straight");

    }
    if (ThreeOfKind == true){
        System.out.println("The sfirst hand has a straight");

    }
    if (ThreeOfKind2 == true){
        System.out.println("The second hand has a straight");

    }


    System.out.println(isThisPair2);
    System.out.println(isThisPair);

    System.out.println(isStrait);
    System.out.println(isFlush);





    //call the card hierarchy class
    // TODO Auto-generated method stub
    return 0;
}



}
Robert Jimen
  • 1
  • 1
  • 1
  • What is the logic for `isSameFace()` method in your `Card` class? – PM 77-1 Oct 28 '14 at 20:28
  • i am not sure about the meaning of your isPair() and ThreeOfAKind() method. Are they supposed to check whether the current hand is only a pair (a three of a kind) or whether it includes a pair (but possible also a three of a kind). – markus Oct 28 '14 at 20:29
  • A word of advice: when evaluating poker hands this way (i.e., testing hand types rather than using sophisticated lookup-table techniques), three things are essential: (1) sort the cards in rank order high-to-low, and (2) test each hand type from top down, i.e., look for straight flushes first, then quads, then full houses, etc., leaving no-pair for last, and (3) don't forget to special-case the wheel (A2345 straight). – Lee Daniel Crocker Oct 28 '14 at 21:28
  • One more piece of advice: before using `theCards.size()` to end your loop, assert that it equals 5. Poker hands have exactly 5 cards, no more, no less. Seven-card games and such are handled by individually evaluating each 5-card combination legal for that game and picking the best one. Trying to account for these at the same time is impossible. – Lee Daniel Crocker Oct 28 '14 at 22:35

3 Answers3

2

Use a HashMap to count the number of times a given card rank appears in the hand. Iterate through your hand. If the card's rank does not exist in the map, insert it with a value of 1. If the card's value already exists in the map, increment the value by 1. Then any key-value pair with a value of 3 is trips. It's trivially easy to adapt this concept to look for pairs, full boat, quads.

There's the concept, now implement the code.

MarsAtomic
  • 10,436
  • 5
  • 35
  • 56
  • 2
    @tnw Thank you, kindly. We only help ourselves by encouraging active thinking, since one day, we might have to debug this person's code. :) – MarsAtomic Oct 28 '14 at 20:30
  • If you have an array of five cards sorted by rank, you can determine the presence of three-of-a-kind with no more than three comparisons. Building a HashMap would be a horrible waste of time. – Lee Daniel Crocker Oct 28 '14 at 21:34
0

Looking at your code, I would advise you use a for loop instead of an enhanced for loop for iterating through it. In fact, I would suggest you use an Iterator if you've gone over it already, but if not, you can use Collections frequency method which counts how many times something appears in a collection. You could make a temporary set with the values in the ArrayList, which should get rid of duplicates, and you can use a For Each loop with the set's non-duplicate to find the amount of duplicates in the original ArrayList.

Louis Jenkins
  • 391
  • 1
  • 2
  • 10
0

Disregard the different variables. This is how I did mine in my project.

boolean hasThreeOfAKind = false;
        int[] value = new int[cards.length];
        for(int i =0; i<cards.length; i++){
            Card myCard = cards[i];
            value[i] = myCard.getValue(); //an array that stores the values of the cards passed in
        }
        int counter = 0;
        for(int i =0; i<cards.length; i++){
            for(int j =i+1; j<cards.length; j++){
                if(value[i] == value[j]){
                    counter++; //if a pair is found increment the counter
                }
                if(j == cards.length-1 && counter!=2){ //if the array of values has been looped
                                                       //through and a second "pair" of the same 
                                                       //value hasn't been found.
                    counter = 0; //start again
                }
//if the array has been looped through and 3 cards of the same value has been found
                else if(j== cards.length-1 && counter >= 2){
                    hasThreeOfAKind = true;
                }
            }
        }

        return hasThreeOfAKind;