質問
私はC#でポーカーフレームワークを書いていますが、現在持っているデザインが好きではありません。私の目標は、バッチモードで複数のAIエージェントを非常に迅速に互いに対戦させることができるゲームエンジンを使用し、複数のAIエージェントと複数の人間をプレイすることです(おそらくSilverlightクライアントを介して)。効率を高く保ちたいのですが、柔軟性を維持したいと思います。たとえば、Limit'em、No-Limit Hold'em、Limit 7-Card Studなどのゲームをプレイできるはずです。
私の現在のデザインはかなり不格好で柔軟性がありません:
- Handhistory:現在の手に関するすべての情報が含まれています(プレイヤーのプレイヤー、ベットメイドなど)
- iPlayer:すべてのプレイヤーは、GetAction(Handhistory History)メソッドを定義します。
- GameEngine:Handhistoryオブジェクトを返すPlay(HandInfo Info)メソッドを定義します。
- Potmanager:ポットを管理し、各プレイヤーがどれだけ電話しなければならないか、どれだけ勝つことができるかを決定します(例えば、不平等なスタックがあり、オールインである場合)。
- BetManager:ベットを管理し、ベットラウンドがいつ終了するかを決定します。
HandINFOクラスには、ハンドのセットアップ方法に関するすべての情報が含まれています。プレイ方法は次のようになります:
HandHistory Play(HandInfo info)
{
PotManager pots = new PotManager(info);
BetManager bets = new BetManager(info);
HandHistory history = CreateHistory(info);
bets.CollectBlinds();
if(!bets.GameOver)
{
DealHoleCards();
if(bets.PlayersThatCanStillBet > 1)
bets.CollectBets();
if(!bets.GameOver)
{
DealFlop();
... and on and on
}
}
return history;
}
ブラインドなどを収集するなど、考慮すべきことが非常に多いため、問題が発生します。ポットとベットマネージャーのクラスは悪夢になり、常にバグに悩まされています。また、私のエンジンデザインは、他のゲームとは対照的に、1つのゲームタイプ(Hold'em)のみをサポートしています。
私のメインランキングは、エンジンが主に数十億の手よりもAIシミュレーターとして使用されるため、効率性のために最初です。しかし、私はこれができるよりエレガントな方法があると思いたいです。
解決
私の最初の考えは、最初に読みやすさと冗長性の欠如のコードと、パフォーマンスを最適化することです(これは効率とは意味があると思います)。通常、パフォーマンスボトルの首がどこにあるかを予測するのは困難であり、少し遅いアプリは、バギーまたは維持不可能なシステムよりも優れています。のような製品を簡単に使用できます ドットレース 最適化する準備ができたら、それが十分に速くないことがわかった場合。
機能を追加したいというあなたの欲求に関しては、より良くなることをお勧めします リファクタリング. 。これは、TDDの中核的なプリピューールの1つです。最小量のコードを記述して機能を完了し、コードの匂いをリファクタリングします。また、TDDを使用することで、たとえばスタッドを実装したときに、Hold'emがまだ機能していることを確認できます。
リファクタリングから始めるのに適した場所は、あなたがすでに保守性の問題に遭遇しているように聞こえるので、各クラスに単一の責任を持っていることを確認することです(最初の責任があります しっかりとしたプリピューール)。あなたの例の方法には、賭け、取引、ゲームの履歴など、多くの責任があります。
他のヒント
私はインターフェースが本当に好きでした IOpponent
それはによって書かれました John Gietzen
戦艦AIトーナメント向け。インスピレーションのために彼のフレームワークを見てみましょう。
ああ、私は最近これを見ました:http://visualstudiogallery.msdn.microsoft.com/en-us/ba4638ad-a2d2-49e5-ae46-94e0f747cae0?src=vside