C# Base Keyword Problem

Base Keyword appears tp reference derived class rather than base class

Page 1 of 1

7 Replies - 2232 Views - Last Post: 16 August 2010 - 09:35 AM Rate Topic: -----

#1 Guest_Jason*


Reputation:

C# Base Keyword Problem

Posted 16 August 2010 - 08:03 AM

Hello everybody. I am sorry for the wall of text, but please take the time to read as I am guessing it may be a quite easy problem to solve for someone with slightly more experience than I have. Thanks.

I am making a card dealer class, a player class, a card class and a blackjack/main class. These will, in my current project, come together to make a blackjack game. However, I have hit a problem. Basically, I have a method that deals the cards. The method basically uses the deck of shuffled cards and 'pops' one card at a time out and stores them in a hand. Currently, I have added functionality to specify how many cards to deal in total, and the method deal alternately to player and dealer (1 to dealer, 1 to player, 1 to dealer etc). The cards are then stored in a stack. Each stack represents a hand. I basically have a hand field (and properties) in the player class. Dealer then inherits from the player class. Therefore, Dealer automatically has it's own hand field also.

I am, from the dealer method in the dealer class, trying to assign 1 card to the dealer using the 'this' keyword (intellisense confirms that the 'this' keyword does indeed reference the current instance of the deal class) and then the next card to the hand field in the player class using the 'base' to keyword (which does reference the player instance according to intellisense). Everything seems fine. However, when I run the code, I find that every single card is being assigned to the dealer class's inherited hand field, and none of the cards are being assigned to the player class's hand field. Effectively, the 'base' keyword is acting like the 'this' keyword for some reason. I have a feeling it is something to do with how I have handled the contructors of both the classes, but,being quite new c#, I haven't quite got the knowledge to know the exact cause of the problem. Any help would be greatly appreciated! Below are the Dealer and Player classes:

Dealer

namespace Games
{
    //GOOD

    public class Dealer:Player
    {
        //Fields
        private static Stack<Card> shuffledCardDeck;
        private static Card[] unshuffledCardDeck; //get built deck from constructor. The constructor is called in the
                                                 // black jackclass and gets the deck from the Card class's buildDeck method 

        //properties
        public Stack<Card> getSetShuffledDeck
        {

            get { return shuffledCardDeck; }
           

        }

        //Constructors
      
        public Dealer(Card [] cards) :base()
        {
            shuffledCardDeck = null;
            unshuffledCardDeck = cards;
           
        }
       

        //Methods

        public static void shuffleCards() //shuffles deck and places the cards in a stack which is stored in the shuffledDeck field
        {

            Random ran = new Random();

            for (int i = 0; i < unshuffledCardDeck.Length; i++)
            {
                int j = ran.Next(unshuffledCardDeck.Length - 1);
                Card temp = unshuffledCardDeck[i];
                unshuffledCardDeck[i] = unshuffledCardDeck[j];
                unshuffledCardDeck[j] = temp; 
            }
            
            shuffledCardDeck = new Stack<Card>();
            
            foreach (Card cardArrayElements in unshuffledCardDeck)
            {

                shuffledCardDeck.Push(cardArrayElements);

            }

        }

        public void dealCards(int totalNumberToDeal)//problem method - should put cards from shuffledDeck in the hand fields of the Dealer and Player class alternatively.
                                                   //All cards are put into the Dealer class's hand inherited hand field though.
        {


            int i =0;
            int j = 0;

            while (i < totalNumberToDeal)
            {
                if (j % 2 != 0)
                {
                    this.setHand = shuffledCardDeck.Pop(); //set hand is the property in the Player class for adding cards to the hand field
                }
                else                                       //BOTH these statements add cards to the dealer's inherited hand field. The second statement does the same as the first???
                {
                    base.setHand = shuffledCardDeck.Pop();
                
                }

                j++;
                i++;

            }

        }


    }
}



Player

namespace Games
{
    public class Player:IBlackJack
    {
        //GOOD

        //Fields
        private Stack<Card> hand;//Field where hands are stored
        

        //Properties
        public Stack<Card> getHand
        {
        get {return hand;}

        }
        public int getSetBet
        {
            get;
            set;

        }
        public int getSetBalance
        {
            get;
            set;

        }

        public int getSetTotals
        {
            get;
            set;
        }

        public bool IsDoubled
        {
            get;
            set;

        }

        public Card setHand{ //sets hand by receiving cards to 'push' into hand field

            set { hand.Push(value); }
        }

        //Constructors

        public Player() { hand = new Stack<Card>(); }//run when instance of Dealer class is created as dealer doesn't have a balance and doesn't bet

        public Player(int defaultBet,int currentBalance)//default bet can be thought to be the common bet a player makes
        {
            getSetBet = defaultBet;
            getSetBalance = currentBalance;
            hand = new Stack<Card>();
        }

        //Methods

        public void playCards(TextBox cardListTextBox, int numberOfCards)
        {
            int i = 0;//controls number of cards to be played

            foreach (Card c in hand)
            {
                if (i == numberOfCards) break;

                cardListTextBox.Text += String.Format("{0}\r\n", c.Name); //Cards are, at the moment, still kept in the hand after they have been played

                i++;
            }

            int j = 0;//controls number of cards to be removed from stack (as they have been played in the previous statement)

            while (j < numberOfCards)
            {
                
                hand.Pop();
                i++;
            }
        }

    }
}




Here is the blackjack class also:

namespace Games
{
    /// <summary>
    /// Interaction logic for Window1.xaml
    /// </summary>
    public partial class Blackjack : Window
    {
       

        //Fields

        private Dealer dealer;
        private Player player;
 


        public Blackjack()
        {
            InitializeComponent();

            
            pbust.Content = String.Empty;
            dbust.Content = String.Empty;


            
            
            //new dealer and pass a deck of unshuffled cards
            dealer = new Dealer(Card.BuildDeck());
            
            //shuffle cards
            Dealer.shuffleCards();
            
            //new player
            player = new Player(10, 100);
            player.IsDoubled = false;
            
            currentBet_txt.Text = String.Format("{0}", player.getSetBet);
            currentBalance_txt.Text = String.Format("{0}", player.getSetBalance);
           
            //Stack<Card> f = dealer.getShuffledDeck;
            //foreach (Card c in f)
            //{
              //  dealerHand.Text += String.Format("{0}\r\n", c.Name);
                
            //}

           
           
        }
        //GOOD
        public int getTotals(Stack<Card> hands)
        {
            int total = 0;

            foreach (Card c in hands)
            {
                if ((c.Value == 1))//check for aces, as they can equal 1 or 11
                {

                    total += c.Value;//increment by 1

                    if (total <= 11)//if total is now 11 or less, it means we could have added 11 to total rather than 1...
                    {

                        total += 10;//...therefore, add 10 to ensure overall increase is 11
                        c.Value = 11;//set value of ace to 11 to maintain correct card object for any particular game

                    }

                }
                else
                {

                    total += c.Value;
                }
            }

            return total;

        }
        //GOOD
        public void doubleBet(object sender, RoutedEventArgs e)
        {

            player.getSetBet *= 2;

        }
        //GOOD
        private void increaseBet_Click(object sender, RoutedEventArgs e)
        {
            if (player.getSetBet >= 100)
            {
                player.getSetBet = 100;

            }
            else
            {

                currentBet_txt.Text = String.Format("{0}", ++player.getSetBet);

            }


        }
        //GOOD
        private void decreaseBet_Click(object sender, RoutedEventArgs e)
        {

            if (player.getSetBet <= 1)
            {

                player.getSetBet = 1;

            }
            else
            {
                currentBet_txt.Text = String.Format("{0}", --player.getSetBet);
            }
        }

        private void deal_btn_Click(object sender, RoutedEventArgs e)
        {
            deal_btn.IsEnabled = false;
            dealer.dealCards(4);
            
                dealerHand_txt.Text = String.Format("{0}", dealer.getHand.Count);

            
           
            //player.playCards(playerHand_txt, 2);   //This method, implemented in the player class to play the cards, doesn't function properly because the hand field is 'an 
                                                     //empty stack', due to the fact that the cards
                                                     // are not being added to the Player instance's hand field from the deal the Dealer class  
           // dealer.playCards(dealerHand_txt, 1)

        }
    }
}
        



Thanks a LOT for your time. I really appreciate it.

Is This A Good Question/Topic? 0

Replies To: C# Base Keyword Problem

#2 Guest_Jason*


Reputation:

Re: C# Base Keyword Problem

Posted 16 August 2010 - 08:06 AM

The method on line 57 in the Dealer class is the apparent problem area (with the 'base' word acting like the 'this' keyword).
Was This Post Helpful? 0

#3 Curtis Rutland  Icon User is online

  • (╯□)╯︵ (~ .o.)~
  • member icon


Reputation: 4430
  • View blog
  • Posts: 7,701
  • Joined: 08-June 10

Re: C# Base Keyword Problem

Posted 16 August 2010 - 08:28 AM

"base" does not refer to a different instance than "this." They both point to the same object, but "this" is a reference to the object as the derived class, and "base" is a reference as the base class.

If you're making Player a base class and Dealer an inherited version of player, you not be doing it the best way.

Here's the concept. Let me give you an over-simplified example:
class Program
{
    static void Main(string[] args)
    {
        Person q = new Person();
        q.Talk();
        Programmer p = new Programmer();
        p.Talk();
        p.BaseTalk();
        Console.ReadKey();
    }
}

public class Person
{
    public virtual string ToSay 
      { get { return "Hi Everybody!"; } }
    public virtual void Talk() 
      { Console.WriteLine(ToSay); }

    public Person() 
     { }
}

public class Programmer : Person
{
    public override string ToSay 
      { get { return "Hello World"; } }
    public override void Talk() 
      { Console.WriteLine(ToSay); }
    public void BaseTalk() 
      { base.Talk(); }

    public Programmer() : base() 
      { }
}



The output of this program is:

Quote

Hi Everybody!
Hello World
Hello World


You'll notice that by calling base.Talk, it's not using a different object, but the same. ToSay is set in both the base class and the derived class, but you'll notice even when you use base.Talk, it uses the value from the derived ToSay.

You'll need separate classes for your dealer and your player. Perhaps make an abstract "Person" class that holds a stack for a hand, and abstract methods for things like Play. Then implement then differently in each derived class.

This post has been edited by insertAlias: 16 August 2010 - 08:29 AM

Was This Post Helpful? 3
  • +
  • -

#4 Guest_Jason*


Reputation:

Re: C# Base Keyword Problem

Posted 16 August 2010 - 09:07 AM

Wow! Thank you very much for taking the time to do that, I really appreciate it. That has made it much...much clearer! I definately had the meaning of the 'base' keyword confused in my mind.

So, is there no real way I can create a solid and efficient application the application with the current class hierachy? My thinking when I created it was probably over - simplified to be fair.

I was thinking (for the black jack game anyway), a dealer 'is-a' player as a dealer plays cards, has a hand, and the player plays against the dealer. Therefore, at the time, it seemed logical to implement the standard behaviours common to a player, and then just add dealer associated functionality also. Consequently, dealer inhrits from player. Then, obviously, the Blackjack class would hold both these objects as a blackjack game 'has(-a)' a player and a dealer. I could then use the player and dealer classes in other card game applications I create (if I make them 'generic' enough).

Was this not the correct way to think about it then? I would really appreciate your advice and input of knowledge on this too while your here as, being new to programming in general really, these are the kind of OO principles I really need to learn and get nailed down in my mind.
Was This Post Helpful? 0

#5 Curtis Rutland  Icon User is online

  • (╯□)╯︵ (~ .o.)~
  • member icon


Reputation: 4430
  • View blog
  • Posts: 7,701
  • Joined: 08-June 10

Re: C# Base Keyword Problem

Posted 16 August 2010 - 09:10 AM

Well, I can see the dealer-is-a-player relationship. You could make it work.

Just remember to make an instance of a dealer, and an instance of a player. Not just one. :)
Was This Post Helpful? 0
  • +
  • -

#6 Guest_Jason*


Reputation:

Re: C# Base Keyword Problem

Posted 16 August 2010 - 09:23 AM

Thanks for the quick reply. I have created a instance of both player and dealer (I think :unsure:) in the blackjack class. The blackjack class implements the rules of the a blackjack game, and a blackjack game has a dealer and a player, and so I created an instance of both in the blackjack class.

So, just to clarify, there is no way in which I can set a player instance version of hand from within the dealer class instance? Therefore, I am going to have to restructure and find another way to deal out the cards?

Thanks again.
Was This Post Helpful? 0

#7 Curtis Rutland  Icon User is online

  • (╯□)╯︵ (~ .o.)~
  • member icon


Reputation: 4430
  • View blog
  • Posts: 7,701
  • Joined: 08-June 10

Re: C# Base Keyword Problem

Posted 16 August 2010 - 09:26 AM

View PostJason, on 16 August 2010 - 03:23 PM, said:

So, just to clarify, there is no way in which I can set a player instance version of hand from within the dealer class instance? Therefore, I am going to have to restructure and find another way to deal out the cards?


There's never "no way" to do pretty much anything. But the question is: "is it the best way?"

It's entirely possible to expose a public Player in the Dealer class. Better yet, you could use a List<Player> if you want to make it multiplayer.

You could add a property to Dealer:
public Player HumanPlayer {get;set;}
...
...
...
Player player = new Player();
Dealer dealer = new Dealer();
dealer.HumanPlayer = player;


Then you could refer to it from inside Dealer with this.HumanPlayer.

This post has been edited by insertAlias: 16 August 2010 - 09:27 AM

Was This Post Helpful? 0
  • +
  • -

#8 Guest_Jason*


Reputation:

Re: C# Base Keyword Problem

Posted 16 August 2010 - 09:35 AM

Yes, I do very much agree with the idea of 'is it the best way?'. At the end of the day, I am always trying to model the problem in the best and most efficient way possible (despite the fact I am still very much a beginner) as, in my mind, that's the only way to do things. Thanks a lot for all the time you've given me here. You have been a great help and have given me a few things to think about at the same time. What more could a learner ask for? :bigsmile:

Thanks a lot.
Jason
Was This Post Helpful? 0

Page 1 of 1