void Calculate()
 {
     foreach (Pocket p in _pockets)
     {
         _mPocket = new CardSet(
             StdDeck.Descriptor.CardSets[(int)p._c1],
             StdDeck.Descriptor.CardSets[(int)p._c2]);
         List <double> evList = new List <double>(1225);
         for (int c1 = StdDeck.Descriptor.Size - 1; c1 >= 0; --c1)
         {
             CardSet m1 = StdDeck.Descriptor.CardSets[c1];
             if (m1.IsIntersectingWith(_mPocket))
             {
                 continue;
             }
             for (int c2 = c1 - 1; c2 >= 0; --c2)
             {
                 CardSet m2 = new CardSet(m1, StdDeck.Descriptor.CardSets[c2]);
                 if (m2.IsIntersectingWith(_mPocket))
                 {
                     continue;
                 }
                 _evCount = 0;
                 _mOther  = m2;
                 CardEnum.Combin(StdDeck.Descriptor, 5, CardSet.Empty, _mPocket | m2, Evaluate);
                 double ev = 0.5 * _evCount / _boardsCount;
                 p._evDict.Add(m2, ev);
             }
         }
     }
 }
Example #2
0
        public void Test_Random()
        {
            int REPETITIONS = 100;

#if DEBUG
            REPETITIONS = 8;
#endif

            int seed = (int)DateTime.Now.Ticks;
            Console.WriteLine("Random seed {0}", seed);
            Random rand = new Random(seed);
            _cardRng = new SequenceRng(seed);
            _cardRng.SetSequence(StdDeck.Descriptor.FullDeckIndexes);
            for (int r = 0; r < REPETITIONS; ++r)
            {
                _enumCount = r % 7;
                int sharedCount = rand.Next(0, StdDeck.Descriptor.Size + 1 - _enumCount);
                int deadCount   = rand.Next(0, StdDeck.Descriptor.Size + 1 - sharedCount - _enumCount);

                _cardRng.Shuffle(sharedCount + deadCount);
                int rc = 0;

                _shared = new CardSet();
                for (int i = 0; i < sharedCount; ++i)
                {
                    _shared |= StdDeck.Descriptor.CardSets[_cardRng.Sequence[rc++]];
                }

                _dead = new CardSet();
                for (int i = 0; i < deadCount; ++i)
                {
                    _dead |= StdDeck.Descriptor.CardSets[_cardRng.Sequence[rc++]];
                }
                Debug.Assert(rc == sharedCount + deadCount);
                Debug.Assert(!_shared.IsIntersectingWith(_dead));

                //Console.WriteLine("B: {0:x16} D:{1:x16}", board, dead);
                _combinationsCount = 0;
                _lastCs            = 0;
                CardEnum.Combin(StdDeck.Descriptor, _enumCount, _shared, _dead, VerifyCombination);
                Assert.AreEqual(EnumAlgos.CountCombin(StdDeck.Descriptor.Size - sharedCount - deadCount, _enumCount), _combinationsCount);

                _combinationsCount1 = 0;
                _lastCs1            = 0;
                CardEnum.Combin(StdDeck.Descriptor, _enumCount, _shared, _dead, VerifyCombinationParam, _combinationsCount);
                Assert.AreEqual(EnumAlgos.CountCombin(StdDeck.Descriptor.Size - sharedCount - deadCount, _enumCount), _combinationsCount1);

                _combinationsCount1 = 0;
                _lastCs1            = 0;
                int[] cards = new int[_enumCount + sharedCount].Fill(-1);
                StdDeck.Descriptor.GetIndexesAscending(_shared).ToArray().CopyTo(cards, 0);
                int[] deadIdx = StdDeck.Descriptor.GetIndexesAscending(_shared | _dead).ToArray();

                CardEnum.Combin(StdDeck.Descriptor, _enumCount, cards, sharedCount, deadIdx, deadIdx.Length, VerifyCombinationParam, _combinationsCount);
                Assert.AreEqual(EnumAlgos.CountCombin(StdDeck.Descriptor.Size - sharedCount - deadCount, _enumCount), _combinationsCount1);
            }
            Console.WriteLine("{0} repetitions done.", REPETITIONS);
        }
 public void SetMask(int cardCount)
 {
     CardSet.Clear();
     for (int i = 0; i < cardCount; ++i)
     {
         Debug.Assert(!CardSet.IsIntersectingWith(StdDeck.Descriptor.CardSets[Cards[i]]));
         CardSet.UnionWith(StdDeck.Descriptor.CardSets[Cards[i]]);
     }
 }
        static int Showdown(CardSet ourPocket, CardSet oppPocket, CardSet board, int handSize)
        {
            Debug.Assert(!ourPocket.IsIntersectingWith(oppPocket));
            Debug.Assert(!ourPocket.IsIntersectingWith(board));
            Debug.Assert(!ourPocket.IsIntersectingWith(board));

            CardSet ourHand = new CardSet(ourPocket, board);
            CardSet oppHand = new CardSet(oppPocket, board);

            UInt32 ourRank = CardSetEvaluator.Evaluate(ref ourHand);
            UInt32 oppRank = CardSetEvaluator.Evaluate(ref oppHand);

            if (ourRank > oppRank)
            {
                return(1);
            }
            else if (ourRank < oppRank)
            {
                return(-1);
            }
            return(0);
        }
Example #5
0
        void CombinRecursive(
            // Deck parameters
            CardSet[] deck, int suitCount, int deckSize,
            // Initial call parameters
            int n,
            // Algorithm parameters
            int depth, CardSet result1, int r1, int s1, int maxSuit,
            // Debug and test parameters
            ref int counter
            )
        {
            if (depth == n)
            {
                Debug.Assert(result1.CountCards() == n);
                counter++;
                _list.Add(result1);
                if (Verbose)
                {
                    Console.WriteLine("{0,6}: {1}", counter, result1);
                }
                return;
            }
            int r2 = r1;
            int s2 = s1 + 1;

            if (s2 >= suitCount)
            {
                s2 = 0;
                r2++;
            }

            for (; (r2 + s2) < deckSize + 1 - (n - depth);)
            {
                int maxSuit2 = r2 == r1 ? maxSuit : Math.Max(maxSuit, s2);
                //int maxSuit2 = Math.Max(maxSuit, s2);
                CardSet result2 = deck[r2 + s2];
                Debug.Assert(!result2.IsIntersectingWith(result1));
                result2.UnionWith(result1);
                CombinRecursive(deck, suitCount, deckSize, n, depth + 1, result2, r2, s2, maxSuit2, ref counter);
                s2++;
                if (s2 > Math.Min(maxSuit + 1, suitCount - 1))
                {
                    s2  = 0;
                    r2 += suitCount;
                }
            }
        }
Example #6
0
        private void VerifyCombination(ref CardSet cs)
        {
            _combinationsCount++;
            Assert.IsFalse(cs.IsIntersectingWith(_dead));
            Assert.IsTrue(cs.Contains(_shared));
            CardSet uniqueMask = new CardSet {
                bits = cs.bits & (~_shared.bits)
            };

            Assert.AreEqual(_enumCount, uniqueMask.CountCards());
            // Use the fact that CardEnum generate masks in ascending order to check uniqueness
            if (_enumCount > 0)
            {
                Assert.Greater(uniqueMask.bits, _lastCs);
            }
            _lastCs = uniqueMask.bits;
        }
        void OnCombinLinkStates(CardSet srcCards, int count)
        {
            // Find the state for theses cards. No search is necessary here,
            // as the cards are dealt in the same order as in creation, we can use _combinCount.
            int srcMapIdx = _combinCount;

            Debug.Assert(_cardsToState[count][srcMapIdx].Cards == srcCards);
            State srcState = _states[_cardsToState[count][srcMapIdx].StateId];

            // Deal next cards.
            for (int c = 0; c < 52; ++c)
            {
                if (srcState.Table[c] != 0)
                {
                    // Already linked
                    continue;
                }
                CardSet newCard = StdDeck.Descriptor.CardSets[c];
                if (newCard.IsIntersectingWith(srcCards))
                {
                    // Impossible card.
                    continue;
                }
                CardSet dstCards = newCard | srcCards;
                int     linkValue;
                if (count + 1 < _maxHandSize)
                {
                    // Link to state
                    int dstMapIdx = Array.BinarySearch(_cardsToState[count + 1], new CardsToState {
                        Cards = dstCards
                    });
                    Debug.Assert(_cardsToState[count + 1][dstMapIdx].Cards == dstCards);
                    State dstState = _states[_cardsToState[count + 1][dstMapIdx].StateId];
                    linkValue = dstState.Id;
                }
                else
                {
                    // Link to hand value.
                    linkValue = (int)CardSetEvaluator.Evaluate(ref dstCards);
                }
                srcState.Table[c] = linkValue;
            }
            _combinCount++;
        }
 private void FillFinalHands(State state, CardSet cards)
 {
     for (int c = 0; c < 52; ++c)
     {
         if (state.Table[c] != 0)
         {
             // Already done.
             continue;
         }
         CardSet nextCard = StdDeck.Descriptor.CardSets[c];
         if (nextCard.IsIntersectingWith(cards))
         {
             continue;
         }
         CardSet finalHand = cards | nextCard;
         Debug.Assert(finalHand.CountCards() == _maxHandSize);
         UInt32 handRank = CardSetEvaluator.Evaluate(ref finalHand);
         state.Table[c] = (Int32)handRank;
     }
 }
Example #9
0
        private void VerifyCombinationParam(int [] cards, int param)
        {
            CardSet cs = StdDeck.Descriptor.GetCardSet(cards);

            Assert.AreEqual(_combinationsCount, param);
            _combinationsCount1++;
            Assert.IsFalse(cs.IsIntersectingWith(_dead));
            Assert.IsTrue(cs.Contains(_shared));
            CardSet uniqueCs = new CardSet {
                bits = cs.bits & (~_shared.bits)
            };

            Assert.AreEqual(_enumCount, uniqueCs.CountCards());
            // Use the fact that CardEnum generate masks in ascending order to check uniqueness
            if (_enumCount > 0)
            {
                Assert.Greater(uniqueCs.bits, _lastCs1);
            }
            _lastCs1 = uniqueCs.bits;
        }
Example #10
0
        public GameRecord Generate(int repetition)
        {
            string[][] enumNames   = new string[_enumCounts.Count][];
            int[]      enumIndexes = new int[_enumCounts.Count];
            CardSet    deadCards   = _fixedCards;

            if (_enumCounts.Count != 0)
            {
                int r = repetition;
                for (int d = _enumCounts.Count - 1; d >= 0; --d)
                {
                    enumIndexes[d] = r % (int)_enumCombosCounts[d];
                    r /= (int)_enumCombosCounts[d];
                }
                int redealFrom = _enumCombos.Count;
                for (int d = _enumCounts.Count - 1; d >= 0; --d)
                {
                    if (enumIndexes[d] != 0)
                    {
                        break;
                    }
                    redealFrom = d;
                }
                for (int d = 0; d < redealFrom; ++d)
                {
                    deadCards.UnionWith(_enumCombos[d][enumIndexes[d]]);
                }
                for (int d = redealFrom; d < _enumCombos.Count; ++d)
                {
                    _enumCombos[d].Clear();
                    CardEnum.Combin(_deckDescr, _enumCounts[d], CardSet.Empty, deadCards, OnCombin, d);
                    Debug.Assert(_enumCombosCounts[d] == _enumCombos[d].Count);
                    deadCards.UnionWith(_enumCombos[d][enumIndexes[d]]);
                }
                for (int d = 0; d < _enumCombos.Count; ++d)
                {
                    string enumCards = _deckDescr.GetCardNames(_enumCombos[d][enumIndexes[d]]);
                    enumNames[d] = enumCards.Split(_separator, StringSplitOptions.RemoveEmptyEntries);
                }
            }

            GameRecord result = new GameRecord(_cfg.ToString());

            result.Actions.Clear();

            // Shuffle the rest of the deck.
            CardSet deckRest = _deckDescr.FullDeck;

            deckRest.Remove(deadCards);
            _randomDealer.SetSequence(_deckDescr.GetIndexesAscending(deckRest).ToArray());
            _randomDealer.Shuffle(_randomCount);

            int randomDealt = 0;

            int[] enumDealt = new int[_enumCounts.Count];
            // Deal the cards.
            for (int a = 0; a < _cfg.Actions.Count; ++a)
            {
                PokerAction action = _cfg.Actions[a];
                if (!action.IsDealerAction())
                {
                    continue;
                }
                string[] cards       = action.Cards.Split(_separator, StringSplitOptions.RemoveEmptyEntries);
                CardSet  resultCards = new CardSet();
                foreach (string card in cards)
                {
                    CardSet nextCard = new CardSet();
                    if (card == "?")
                    {
                        nextCard = _deckDescr.GetCardSet(_randomDealer.Sequence, randomDealt++, 1);
                    }
                    else if (card.Length > 0 && card.Substring(0, 1) == "#")
                    {
                        int    d        = int.Parse(card.Substring(1));
                        string enumName = enumNames[d][enumDealt[d]++];
                        nextCard = _deckDescr.GetCardSet(enumName);
                    }
                    else
                    {
                        nextCard = _deckDescr.GetCardSet(card);
                    }
                    Debug.Assert(!resultCards.IsIntersectingWith(nextCard));
                    resultCards.UnionWith(nextCard);
                }

                PokerAction resultAction = new PokerAction(action.Kind, action.Position, action.Amount,
                                                           _deckDescr.GetCardNames(resultCards));
                result.Actions.Add(resultAction);
            }
            Debug.Assert(_randomCount == randomDealt);
            return(result);
        }
Example #11
0
        bool FinalizeDeal(ref string currentDeal)
        {
            if (currentDeal == "")
            {
                return true;
            }
            if (_gameState.IsPlayerActing(_position))
            {
                ShowMessage("Is's agents turn");
                return false;
            }
            List<Ak> allowedActions = _gameState.GetAllowedActions(GameDef);
            if (!allowedActions.Contains(Ak.d))
            {
                ShowMessage(string.Format("Wrong action: 'd', expected: '{0}'", ActionKindListToString(allowedActions)));
                return false;
            }
            CardSet cs = StdDeck.Descriptor.GetCardSet(currentDeal);

            int dealRound = _gameState.Round +1;
            int expectedCardsCount = dealRound == 0 ? GameDef.PrivateCardsCount[dealRound] : GameDef.SharedCardsCount[dealRound];
            if (cs.CountCards() != expectedCardsCount)
            {
                ShowMessage(string.Format("Wrong cards count: {0}, expected: {1}", cs.CountCards(), expectedCardsCount));
                return false;
            }

            if(cs.IsIntersectingWith(_dealtCards))
            {
                ShowMessage(string.Format("Some of cards {0} are already dealt", currentDeal));
                return false;
            }
            _dealtCards |= cs;

            PokerAction pa = new PokerAction {Kind = Ak.d, Cards = currentDeal};
            currentDeal = "";
            if (_gameState.Round == -1)
            {
                PokerAction oppPrivateDeal = new PokerAction { Kind = Ak.d, Cards = "" };
                if (_position == 0)
                {
                    pa.Position = 0;
                    oppPrivateDeal.Position = 1;
                    _gameRecord.Actions.Add(pa);
                    _gameRecord.Actions.Add(oppPrivateDeal);
                }
                else
                {
                    pa.Position = 1;
                    oppPrivateDeal.Position = 0;
                    _gameRecord.Actions.Add(oppPrivateDeal);
                    _gameState.UpdateByAction(oppPrivateDeal, GameDef);
                    _gameRecord.Actions.Add(pa);
                }
                _gameState.UpdateByAction(_gameRecord.Actions[_gameRecord.Actions.Count - 2], GameDef);
                _gameState.UpdateByAction(_gameRecord.Actions[_gameRecord.Actions.Count - 1], GameDef);

            }
            else
            {
                pa.Position = -1;
                _gameRecord.Actions.Add(pa);
                _gameState.UpdateByAction(pa, GameDef);
            }
            return true;
        }