Using IEquatable Equals, comparing property of objects in array

883 views Asked by At

I'm attempting to make a flush in a classic poker/card game type program. The property is the suit (hearts, diamonds, etc) and the array is the hand. I used the IEquatable and implemented the Equals method

    public bool Equals(SuperCard otherCard)
    {
        if (otherCard == null)
            return false;
        return (this.cardSuit.Equals(otherCard.cardSuit));
    }

from there in my Program.cs I am writing a bool method for Flush, using the .Equals. it was suggested to me that I use a for loop, but I'm having trouble understanding if I'm doing this right. I need to compare the cardSuit property, card by card. But I'm unsure of how to go about it. Any help would be appreciated. Here's what I have in the method so far.

    private static bool Flush(SuperCard[] hand)
    {
        for (int i = 0; i < hand.Length; i++)
        {
            if (hand[i].Equals(hand[i + 1]) == false)
            {
                return false;
            }
        }
        return hand[hand.Length].Equals(hand[hand.Length - 1]);
    }

in my mind, the for loop compares each card looking for any false's, then returns false if so. outside/after the for loop (supposing theyre all true), I return the true/false of the comparison of the last 2 cards in the the hand. am i over complicating it? is it wrong?

EDIT: I can see this: "if (hand[i].Equals(hand[i + 1]) == false)" will go out of bounds exception, so I need a new way of comparing card to card. Any ideas?

2

There are 2 answers

0
Dmitry Bychenko On BEST ANSWER

First, beware of (possible) stack overflow:

public bool Equals(SuperCard otherCard)
{
    // "otherCard == null" usually calls "Equals" method which in turn 
    // calls "Equals" again and again...
    if (Object.ReferenceEquals(otherCard, null)) // <- No "==" or "Equal" - just reference test
        return false;

    return (this.cardSuit.Equals(otherCard.cardSuit));
}

Another issue is RangeCheckError (see at "Length - 1" in the loop condition)

private static bool Flush(SuperCard[] hand)
{
    if (Object.ReferenceEquals(null, hand))
      return false;

    for (int i = 0; i < hand.Length - 1; i++) // <- Pay attention to "Length - 1"
    {
        if (!hand[i].Equals(hand[i + 1]))     // <- "== false" is quite awkward
        {
            return false;
        }
    }

    // You don't need any additional checks here:
    // A[0] = A[1] = ... = A[length - 1]
    return true;
}
0
Jamiec On

There's a much easier way to do this

private static bool Flush(SuperCard[] hand)
{
    if(hand.Length == 0)
       return false;
    var suit = hand[0].cardSuit;
    return hand.All(c => c.cardSuit == suit);
}