构造函数中的c#结构数组集

构造函数中的c#结构数组集,c#,struct,constructor,C#,Struct,Constructor,我有一个小结构- struct Card { public string suit; public string value; } 然后我用它初始化一组卡片 Card[] deck = new Card[52]; 在Main()中,我调用 它与构造函数相关 public Deck() { int cardNum = 0; for (int i = 0; i < numSuits; i++)

我有一个小结构-

struct Card {
        public string suit;
        public string value;
}
然后我用它初始化一组卡片

Card[] deck = new Card[52];
在Main()中,我调用

它与构造函数相关

public Deck() {         
            int cardNum = 0;
            for (int i = 0; i < numSuits; i++) {
                for (int a = 0; a < numValues; a++) {
                    deck[cardNum].suit = suits[i];
                    deck[cardNum].value = values[a];
                    Console.WriteLine("The card at position " + (cardNum + 1) + " is the " + deck[cardNum].value + " of " + deck[cardNum].suit);
                    cardNum++;

                }
            }

        }
public Deck(){
int-cardNum=0;
对于(int i=0;i
。。。因此,创建一个包含52张卡的牌组,正如我的Console.WriteLine()所确认的那样,它正确地填充了牌组

我的问题是我还有另外两个方法,public void Shuffle()和public string Deal(),正如它们的名字所示,它们分别洗牌和发顶牌,但是我不知道如何将deck.suit和deck.value值传递到上述方法中

我已尝试在构造函数中初始化Card[]数组。所有这些函数都在同一名称空间和类下

我还希望在代码中保留构造函数和两个方法,而不使用任何其他方法,尽管我确信还有许多其他可能更容易做到这一点的方法

提前谢谢

玩一玩这个:

void Main()
{
    var deck = new Deck();
    deck.Shuffle();
    var cards = deck.Deal(1);
    foreach (var card in cards)
    {
        Console.WriteLine($"{card.Value} of {card.Suit}");
    }
}

public struct Card
{
    public Card(string suit, string value)
    {
        this.Suit = suit;
        this.Value = value;
    }
    public readonly string Suit;
    public readonly string Value;
}

public class Deck
{
    private const int _numSuits = 4;
    private const int _numValues = 13;

    private string[] _suits = new [] { "Clubs", "Diamonds", "Hearts", "Spades", };
    private string[] _values = new []
    {
        "Ace", "2", "3", "4", "5", "6", "7", "8", "9", "10", "Jack", "Queen", "King",
    };

    private Card[] _deck = new Card[52];

    public Deck()
    {
        _deck =
            _suits
                .SelectMany(s => _values, (s, v) => new Card(s, v))
                .ToArray();
    }

    private Random _random = new Random();
    public void Shuffle()
    {
        _deck = _deck.OrderBy(_ => _random.Next()).ToArray();
    }

    public Card[] Deal(int take)
    {
        var cards = _deck.Take(take).ToArray();
        _deck = _deck.Skip(take).ToArray();
        return cards;
    }
}

卡片更具普遍性。它们不仅在甲板上使用。它们也用在手上。还有一些游戏甚至在另一个我不知道名字的结构中也有打开的卡片(对不起,我只知道《星际迷航》TNG中的扑克)

根据个人经验,我知道要为“手牌”或“牌组”制作一个合适的类是相当困难的。最终,两者似乎都只是一张卡片的容器[]。因此,使用卡片[]可能更好/更容易。只需要一组静态函数,初始化一整副牌,洗牌,从牌堆中取出一张牌,并将一张牌[]作为参数之一或返回牌实例。请记住,数组本质上是通过引用来处理的,这在这里非常有用

至于随机抽牌而不重复的行为,我个人称之为“彩票问题”。我制作了这个示例代码来处理它:

//Create an array. Fill it with Sequential Numbers.
int[] input = new int[20];

for(int i = 0; i < numbers.lenght; i++)
  input[i] = i;

/*Initialise the instances you will need*/
//Use the array to create a list
List<int> DrawableNumbers = new List<int>(input);
List<int> DrawnNumbers = new List<int>();

//Generate a Random Number Generator
Random rng = new Random();

/*Draw 6 from the group*/
while(DrawnNumbers.Count < 6){
  //Get a random Index to move from DrawableNumbers to DrawnNumbers
  int temp = Random.NextInt(DrawableNumbers.Count);
  DrawnNumbers.Add(DrawableNumbers[i]);
  DrawableNumbers.Remove(temp);
}
//创建一个数组。用序列号填充它。
int[]输入=新的int[20];
对于(int i=0;i

洗牌与洗牌的唯一区别在于,在牌用完之前,你不会停下来。

不幸的是,我还不能评论:

Random rnd=new Random();
Card[] randomOrder = deck.OrderBy(x => rnd.Next()).ToArray();    
//TODO: you could iterate over the random order and fill your Stack 
这将随机洗牌你的数组。 交易应该很简单,你可以选择一个随机的数组索引并返回卡。 如果该卡在发牌后应该被移除,可以使用列表或更好的方法,当你洗牌时,你可以填充创建一张
StackT>
并填充它,然后每次调用
Deal
函数时,你都可以
Pop
下一张卡


@神秘性击败了我,他的解决方案允许一次拿多张牌。问题是,使用堆栈并缓慢清空或使用
时,最好的做法是什么?使用
和新数组?

可静音结构是有害的,只需将其设置为带有属性的类即可。如果您想将其保留为struct(而不是class),请按引用传递。有关无序排列列表或数组,请参阅。
new int[20]()
无效C#。@Enigmativity:谢谢。修正为
int[]input=newint[20]在这里和我的原件中都有。返回
Deal()
的卡数组可以使牌组用完,而无需抛出异常或使用可为空的
卡。这有助于比喻实际发牌——许多游戏一次发一张以上的牌。@Enigmativity正确,我已经投票支持你的解决方案,因为你可以选择每笔交易发一张或多张牌,这是理想的解决方案。我基于德克萨斯州的Hold'Em,你每次只发一张牌。你每次分配牌组时分配一个
随机
对象。这可能会导致中所示的问题。有关备选方案,请参见和。@dbc-是的,您是对的。请注意,我声明它是一个字段,而不是
Shuffle
方法中的变量,这正是您提出的原因。我应该将它声明为
[ThreadStatic]private static Random\u Random=new Random()更安全。非常感谢神秘性,这是一种享受。如果可以的话,我想问你几个后续问题:1。是否有一种方法可以使其在调用deck.Shuffle()时,将以前发过的所有牌重新添加到该牌组中(即deck.Shuffle()将所有52张牌洗牌,不管发过多少张牌)。2.有没有办法让Deal()返回字符串?我尝试修改以从_deck.Take().ToArray()中给我一个字符串变量,但到目前为止没有成功@雷蒙德-当你想要收回所有的卡片时,你通常会创建一个新的
牌组。那么
string
应该返回什么
Deal
呢?
Random rnd=new Random();
Card[] randomOrder = deck.OrderBy(x => rnd.Next()).ToArray();    
//TODO: you could iterate over the random order and fill your Stack