2011-02-28 52 views
7

這是事實第一。洗牌並處理一卡牌的約束

在橋的比賽還有4名 玩家命名的北,南,東,西 。

給每個玩家處理所有52張牌的13張牌 。

有一個榮譽計數系統。 王牌= 4分,王= 3分,王后= 2 分,傑克= 1分。

我創建一個「卡經銷商」有約束其中,例如,你可能會說,手牌到北都有一個完全相同黑桃5和16之間的13榮譽點計數,手中剩下的都是隨機。

如何在不影響「隨機性」的情況下以最佳方式完成此操作,同時還需要有效代碼?

我使用C#和.Net編碼,但在僞代碼中有一些想法會很好!

+0

這個例子是唯一的約束嗎?你能解釋爲什麼這樣的約束?因爲如果約束條件像「北方必須擁有的......」那麼它與「一個玩家必須擁有的......」真的不同。「 – 2011-02-28 15:07:15

+1

不要過分詳細地談論橋牌遊戲,而限制是針對特定的手。通常情況下,如果您爲所有四隻手設置了限制條件,這些限制條件並不複雜。我在這裏的任務的目的是生成董事會實踐特定手牌類型的競價。 – StefanE 2011-02-28 15:26:12

+0

你看過經銷商嗎? – 2011-02-28 15:56:54

回答

2

根據您的計算機的速度有多快,它可能足以做到這一點:

  • 重複:
    • 做了隨機交易
  • 直到板滿足所有限制

與所有性能問題一樣,t他要做的就是試試看!

編輯我試了一下,看到:

done 1000000 hands in 12914 ms, 4424 ok 

這是一個沒有給予任何思想的優化 - 它產生342手每秒會議你的「北有5張黑桃和13-16的榮譽準則點」。我不知道你的申請的細節,但在我看來,這可能就夠了。

+0

剛剛發佈了相同的想法......這將是有趣的,以防止不可克服的約束,所以你的重新處理不會去循環... – 2011-02-28 11:59:14

+0

這真的不會在「有效」的代碼段。我確實在尋找一種欺騙的方法..有22,090,320,000種組合來洗牌,而且會沉重。我打算讓這個在線運行在我的網絡上運行 – StefanE 2011-02-28 12:01:20

+1

這是「有效的」,只要它的行爲如預期。它可能不是非常「高效」,那是真的,但在這種情況下,啓發式解決方法仍然可能是您的最佳選擇。 – 2011-02-28 12:27:15

4

由於這裏的數字非常小,您可以採取啓發式方法:隨機處理您的卡片,評估約束條件,如果不滿足,請重新處理。

1

我會去爲這個流程,我認爲不會影響(不符合限制比修剪解決方案等)的隨機性:在你的程序

  • 名單的「價值」卡的所有可能的組合其榮譽點總數在13至16之間。然後隨機挑選其中一種組合,從新甲板上移除牌。
  • 計算您已經在尊貴卡片中擁有多少黑桃,並隨機挑選剩下的黑桃直到您達到計數。
  • 現在從甲板上選擇儘可能多的非黑桃,非貴重卡,因爲你需要完成這手牌。
  • 最後在其餘的牌中挑選其他牌。

你可以寫我產生第一點的組合,或者乾脆硬編碼它們同時考慮顏色對稱性減少代碼:)行數的程序

+1

該算法不起作用,因爲它會擾亂條件概率。這大概是我的經銷商的「智能堆棧」的工作方式,但是您的第一步不能讓每套價值卡具有相同的概率,因爲填充手其餘部分的方式數量取決於數量您已經選擇的榮譽卡片。我之前提到的經銷商的「智能堆疊」功能可以進行這種分析,但它需要一張非常大的桌子。 – 2011-03-01 16:45:55

+0

例如,如果您獲得5個黑桃和N個榮譽點,那麼您的黑桃服裝的榮譽點數量是多少?在公平交易中,平均得分僅爲N * 5/13。但是你的抽樣技術會產生N/4的平均鏟點。 – 2011-03-01 17:13:15

+0

(Ooops,黑桃的預期點是錯誤的,除非當N = 10,但至少在這種情況下,你的算法將是錯誤的。) – 2011-03-01 19:12:51

1

既然你想練招投標,我想你可能會在未來出現各種形式的限制(而不僅僅是1S開放,因爲我猜這是目前的問題)。試圖想出適合約束條件的最佳手牌生成可能是一個巨大的時間沉沒,並且不值得付出努力。

我建議你使用拒絕採樣:生成一個隨機交易(沒有任何約束),並測試它是否滿足你的約束。

爲了使這個可行,我建議你專注於隨機交易的產生(沒有任何限制)儘可能快。

爲此,將每隻手映射到一個12字節的整數(橋手的總數適合12個字節)。隨機生成一個12字節的整數可以在3,4個字節的隨機數字調用中完成,當然由於手的數量不是恰恰擬合爲12個字節,所以在這裏可能需要一些處理,但我期望它不會太多。

Richard Pavlicek有一個出色的頁面(包含算法)將交易映射到一個數字並返回。

在這裏看到:http://www.rpbridge.net/7z68.htm

我也建議你看一下現有的橋手處理軟件(如Deal 3.1,這是免費提供)了。 Deal 3.1還支持做雙重虛擬分析。也許你可以讓它爲你工作,而不必滾動你自己的。

希望有所幫助。

4

既然有人已經提到了我的Deal 3.1,我想指出我在該代碼中所做的一些優化。首先,爲了獲得最靈活的約束,我想向經銷商添加一個完整的編程語言,以便您可以使用不同類型的評估者和規則生成整個約束庫。我使用了Tcl語言,因爲我已經在學習它的工作,並且在1994年發佈Deal 0.0時,Tcl是在C應用程序中嵌入的最簡單的語言。

其次,我需要約束語言運行相當快。約束在循環內部深處運行。我的經銷商中的很多代碼很少使用查找表等進行優化。

最令人驚訝和簡單的優化之一是在座位上檢查約束之前不對卡片進行處理。例如,如果你想北匹配約束和南部匹配約束B,和你的約束代碼:

match constraint A to north 
match constraint B to south 

那麼只有當你到第一線,你填寫北部手。如果失敗,則拒絕完成交易。如果它通過,接下來要填滿南手並檢查其約束。如果失敗,請拋出整個交易。否則,完成交易並接受它。

我在做一些分析時發現了這種優化,並注意到大部分時間都花在了隨機數生成器中。

有一種奇特的優化,可以在某些情況下工作,稱爲「智能堆棧」。

deal::input smartstack south balanced hcp 20 21 

這生成南的手「工廠」這需要一些時間來建立,但隨後可能很快就會填滿了一方面要符合這個標準。由於條件概率問題,智能堆疊一次只能應用於每筆交易的一隻手。 [*]

智能疊加需要一個「形狀類」 - 在這種情況下,「平衡」,「保持評估器」,在這種情況下,「hcp」和持有評估器的一系列值。 「持有評估人員」是適用於每種訴訟然後合計的任何評估人員,因此hcp,控制人員,失敗人員和hcp_plus_shape等都持有撤回人員。

爲了使智能堆棧有效,持有評估者需要採取相當有限的一組值。智能堆疊如何工作?這可能比我有時間在這裏發佈多一點,但它基本上是一大堆表格。最後一條評論:如果你真的只想要這個程序進行出價練習,而不是模擬,那麼很多這些優化可能是不必要的。這是因爲練習的本質使得它不值得練習非常少見的出價。所以如果你有一個條件只能在十億次交易中出現一次,你可能不會爲此擔心。 :)

[編輯:添加智能堆疊詳情]

好了,正好有8192 = 2^13個可能增持西裝。集團他們的長度和榮譽數:

Holdings(length,points) = { set of holdings with this length and honor count } 

所以

Holdings(3,7) = {AK2, AK3,...,AKT,AQJ} 

,讓

h(length,points) = |Holdings(length,points)| 

現在列出所有符合您的形狀狀態,所有的形狀(黑桃= 5):

5-8-0-0 
5-7-1-0 
5-7-0-1 
... 
5-0-0-8 

請注意,收集所有寶可能的手形尺寸爲560,所以這個列表並不是很大。

對於每個形狀,列出每種套裝列出榮譽點的方式,可以獲得您要查找的總榮譽點數。例如,

Shape Points per suit 
5-4-4-0 10-3-0-0 
5-4-4-0 10-2-1-0 
5-4-4-0 10-1-2-0 
5-4-4-0 10-0-3-0 
5-4-4-0 9-4-0-0 
... 

使用我們的集控股(長度,點),我們可以計算的方式來獲得這些行的數量。 例如,該行5-4-4-0 10-3-0-0,你必須:

h(5,10)*h(4,3)*h(4,0)*h(0,0) 

所以,選擇這些行隨機之一,基於相對概率計數,然後,對於每個訴訟,從正確的Holdings()集合中隨機選擇一個持有。

顯然,手形和點的範圍越廣,需要預先計算的行越多。再多一點的代碼,你仍然可以用一些預先確定的牌來做到這一點 - 如果你知道黑桃王牌或西部牌的什麼地方。

從理論上講,您可以解決這些條件概率問題,以便用多手進行智能堆疊,但問題的解決方案僅對極其罕見的交易類型有效。這是因爲工廠表中的行數大致是一隻手堆疊的行數乘以另一隻手堆疊的行數的乘積。此外,h()表必須以手1,手2和其他手中n個卡的分割方式爲鍵,這將數值的數量從大約2^13改變爲3^13個可能值,大約兩個數量級。

+0

您好托馬斯,謝謝你的一個非常廣泛的答案。我看了你的程序,看起來非常好,即使在我們的工作環境中使用了TCL專家,但我可能會「竊取」一些想法。我的軟件的目的是建立一個網站來解決我和我的合作伙伴進行投標的問題,我們從來沒有時間做到這一點,所以我創建了一個.Net網絡應用程序,以創建一個對應投標系統。如果他們想要,我會讓其他人使用它:) – StefanE 2011-03-01 16:04:19

+0

如果它正在運行一個站點,您可能還想讓一個人上傳交易文件,而不是讓該站點生成交易。然後,您可以使用任何經銷商軟件來生成優惠,然後上傳它們(給定一些合適的格式)。 – 2011-03-01 16:38:04

+0

+1:有關說明。順便說一句,你是否在我的答案中考慮過映射思想?由於隨機數生成是一個瓶頸,將呼叫數從52(或13)減少到4-5將是一個很好的優化。 – 2011-03-01 16:42:15