【问题标题】:How to define and access list in a class - How to access a Player's hand in a Card Game如何在类中定义和访问列表 - 如何在纸牌游戏中访问玩家的手牌
【发布时间】:2014-05-03 19:44:26
【问题描述】:

我意识到这可能以前曾被问过,但我一直在寻找,虽然我在理论上理解我需要做什么,但实际上让它发挥作用的方法正在暗示我。

我正在尝试通过一个项目来学习 C# 和面向对象的编程概念。这个特殊的项目是复制顶级王牌纸牌游戏。我的主题将是权力的游戏。

我的问题是,当我初始化播放器 1 和计算机手时,我对填充它们感到困惑。我可以看到牌从牌组中消失,但我看不到玩家手中的牌(尽管当我对源执行断点/pin 时。我可以看到 cardinHand 填充。

问题是游戏最终得到了 60 张牌(总共)而不是 15 张。(我在创建甲板时加载的 XML 中有 30 行)。 你能检查我的代码,指出我哪里出错了。我知道我需要传递卡片对象,我担心我只是错过了一些简单的东西。我觉得这是重要的部分,因为我想根据玩家手牌的形式显示卡片。

这是 GameStart 方法

public static void startGame()
    {
    Player player1 = new Player();
    Player computer = new Player();

    var newdeck = new Deck();
    newdeck.Shuffle();

    while (newdeck.CountCards() != 0)
    {
        newdeck.dealCards();
    }

    MessageBox.Show("New Game Started");

这是我的甲板课

public class Deck
{

private List<Card> deckofCards = new List<Card>();


//indexer on the deck
// Define the indexer, which will allow client code 
// to use [] notation on the class instance itself. 

public Card this[int i]
{
    get
    {
        // This indexer is very simple, and just returns or sets 
        // the corresponding element from the internal array. 
        return deckofCards[i];
    }
}


public Deck()
{
    resetDeck();
}

public void resetDeck()
{

    XmlDocument xmldata = new XmlDocument();
    xmldata.Load(@"C:\GameofThronesXml.xml");
    XmlNamespaceManager nsmgr = new XmlNamespaceManager(xmldata.NameTable);

    XmlNodeList nodeList;
    XmlElement root = xmldata.DocumentElement;
    nodeList = xmldata.SelectNodes("//CharacterData/record", nsmgr);

    foreach (XmlElement data in nodeList)
    {
        Card singlecard = new Card();
        singlecard.CardID = int.Parse(data.SelectSingleNode("./CardID").InnerText);
        singlecard.Name = data.SelectSingleNode("./Name").InnerText;
        singlecard.Intelligence = int.Parse(data.SelectSingleNode("./Intelligence").InnerText);
        singlecard.Ruthlessness = int.Parse(data.SelectSingleNode("./Ruthlessness").InnerText);
        singlecard.Status = data.SelectSingleNode("./Status").InnerText;
        singlecard.Prestige = int.Parse(data.SelectSingleNode("./Prestige").InnerText);
        singlecard.FightingSkill = int.Parse(data.SelectSingleNode("./FightingSkill").InnerText);
        singlecard.AppearedIn = int.Parse(data.SelectSingleNode("./AppearedIn").InnerText);
        singlecard.Description = data.SelectSingleNode("./Description").InnerText;
        deckofCards.Add(singlecard);
    }

    //string path = @"C:\GameofThronesXml.xml";
    //XElement doc = XElement.Load(path);
    //deckofCards = (from items in doc.Descendants("CharacterData")
    //                select new Card(
    //                        int.Parse(items.Element("CardID").Value),
    //                        items.Element("Picture").Value,
    //                        items.Element("Name").Value,
    //                        int.Parse(items.Element("Intelligence").Value),
    //                        int.Parse(items.Element("Ruthlessness").Value),
    //                        items.Element("Status").Value,
    //                        int.Parse(items.Element("Prestige").Value),
    //                        int.Parse(items.Element("FightingSkill").Value),
    //                        int.Parse(items.Element("AppearedIn").Value),
    //                        items.Element("Description").Value)).ToList();
}

public void Shuffle()
{

    deckofCards = deckofCards.OrderBy(c => Guid.NewGuid())
                 .ToList();

}

public int CountCards()
{

    int number = deckofCards.Count();
    return number;

}

public Card dealCards()
{

    Hand hand = Player.hand;
    //Hand computerHand = Player.hand;

    if (this.deckofCards.Count == 0)
        throw new InvalidOperationException("There are no cards to deal.");

    Card card = deckofCards[0];

    hand.cardsinHand.Add(card);
    deckofCards.RemoveAt(0);
    return card;

 }
}

手课

public class Hand
  {

    /// <summary>
    /// The deck in the hand
    /// </summary>
    public List<Card> cardsinHand = new List<Card>();

    public int GetNumberofCards()
    {
        int count = cardsinHand.Count;
        return count;
    }

    public void AddCard(Card card)
    {
        cardsinHand.Add(card);
    }



}

播放器类

public class Player
{

    public static Hand hand = new Hand();


}

tl;dr - 想要有两个 Player 类的玩家,我可以访问发牌的数量在这种情况下,每个 15 张牌 - 我知道这与 hand.cardsinhand 有关.Count - 我无法使用定义的播放器类访问它。

解决方案 -

        Player Player1 = new Player();
        Player Computer = new Player();

        Deck newdeck = new Deck();
        Hand CompHand = new Hand();
        Hand PlyrHand = new Hand();

        newdeck.Shuffle();

        while (newdeck.CountCards() != 0)
        {
            //The Hand adds the return dealt cards to the respective lists.
            CompHand.AddCard(newdeck.dealCards());
            PlyrHand.AddCard(newdeck.dealCards());
        }

        MessageBox.Show("New Game Started");

        //Snoopy Dance - Each card has 15 cards in each hand.
        MessageBox.Show(CompHand.cardsinHand.Count().ToString());
        MessageBox.Show(PlyrHand.cardsinHand.Count().ToString());

【问题讨论】:

    标签: c# list playing-cards


    【解决方案1】:

    startGame 中的这段代码一直在发牌,直到没有牌为止:

    while (newdeck.CountCards() != 0)
    {
        newdeck.dealCards();
    }
    

    但是dealCards 正在访问静态(即由类的所有实例共享)Player.hand,因此所有卡片都被添加到其中。 (我猜当你为两个玩家添加每张牌时你得到了 60,而当其中一个玩家被注释掉时,你只得到 30,就像问题中一样。)

    您不希望所有玩家共享同一手牌,因此将Player.Hand 更改为非静态(即删除static 关键字)。然后将你的两个初始化玩家的手牌(player1.handcomputer.hand)作为参数传递给dealCards

    public Card dealCards(Hand hand, Hand computerHand)
    ...
    

    我认为有一些关于哪些类负责做什么的整理工作(可以在游戏运行后发布到 codereview.stackexchange.com),但是这种更改应该让你启动并运行。

    【讨论】:

    • 谢谢,这是一个进步,但它抱怨它不能将玩家类转换为手类。唯一的解决方法是将 player1.hand 传递给 dealcards 方法。
    • 对不起,我的错。我已经确定了匹配的答案:直接传递手应该没问题。你可能还想考虑dealCards(为什么是小写的D?)是否应该是Deck的一部分(这不是在做交易的套牌)——也许它属于一个单独的Game类?最好将所有字段(Player.handHand.cardsInHand)设为私有,然后仅添加访问它们所需的公共方法(就像使用 Deck.deckOfCards 一样)。但看起来你进展顺利。也许我会在游戏完成后玩你的游戏:-)
    • 见上文,了解我是如何解决它的(在这一点上 - 我不确定它是否会继续工作。我所知道的是每手牌都有相同的牌
    • 看来您还更改了dealCards() 以从牌组中取出一张牌并将其归还。但我的方法也同样有效。
    • 当我的思路清晰时,我可能会回去使用你的方法。有时您必须选择目前有效的方法:)
    猜你喜欢
    • 1970-01-01
    • 2017-10-06
    • 1970-01-01
    • 1970-01-01
    • 2021-08-18
    • 2016-07-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多