2013-09-26 39 views
2

與關於此主題的許多問題不同,我的作業不是功課。我建立了一個工作的Ghost機器人。我的最終目標是建立一個撲克機器人作爲一種愛好,但Ghost似乎是一個更容易開始考慮的遊戲。Python Ghost Bot

我有問題的代碼如下:

def computer_prompt(playerName,word_string): 
    length_string = len(word_string) 
    for possibilities in wordlist: 
    if possibilities[:length_string].lower() == word_string: 
     if len(possibilities) > 3 and len(possibilities) % 2 != 0: 
     if check_game.is_valid_word(possibilities[length_string],wordlist): 
      if not check_game.word_formed(possibilities[:length_string + 1],wordlist): 
      print(possibilities) 
      return possibilities[:length_string + 1] 

現在,我只希望計算機總是第二,人類總是先走。問題是,雖然電腦幾乎每時每刻都在打我,但有幾次我仍然可以勝過他。例如,如果我演奏「h」,然後他演奏「a」,然後演奏「z」,然後演奏「a」,然後演奏「r」,然後他發出一個錯誤(因爲他不承認失敗:))。

我該如何改變它,讓他知道在這種情況下,我不會說「z」之後再說「a」?很明顯,我可以將這個例子作爲例外編碼,但我想知道這個問題的一般解決方案。一般來說,現在電腦打我,因爲他在決定選擇哪封信之前會查找所有可能的單詞列表,這些單詞將以我的名字結尾。但在「危險」的例子中,他只是被卡住了,我想讓他知道他會卡在前面幾步,這樣他就不會處於第一位...

非常感謝提前!

ADDED 9/27

任何有興趣,下面的代碼似乎有點比我以前有更好的。還不夠完善,但...:

def all_possibilities(word_string, length_string): 
    possibilities = [] 
    for possibility in wordlist: 
     if possibility[:length_string].lower() == word_string: 
     possibilities.append(possibility) 
    return possibilities 

def clear_loser(possibilities): 
    clear_losers = [] 
    for item in possibilities: 
     if len(item) % 2 == 0: 
     clear_losers.append(item) 
    return clear_losers 

def first_n_letters(sub_optimal_computer_possibilities, length_string): 
    first_n_Letters = [] 
    for item in sub_optimal_computer_possibilities: 
    first_n_Letters.append(item[:length_string + 1]) 
    return list(set(first_n_Letters)) 

def existing_Optimal_Move(FIRSTNLETTERS,first_letters_of_clear_losers): 
    length_sub_opt_list = len(FIRSTNLETTERS) 
    new_list = [] 
    for item in FIRSTNLETTERS: 
    if not item in first_letters_of_clear_losers: 
     new_list.append(item) 
    return new_list 

def computer_prompt(word_string): 
    length_string = len(word_string) 
    possibilities = all_possibilities(word_string, length_string) 
    clear_losers = clear_loser(possibilities) #Create list of words that will end on computer 
    sub_optimal_computer_possibilities = [x for x in possibilities if x not in clear_losers] #Create list of words that will end on human (including words that might be suboptimal for me because smart human will make it end on me before getting to this word 
    FIRSTNLETTERS = first_n_letters(sub_optimal_computer_possibilities, length_string) 
    first_letters_of_clear_losers = first_n_letters(clear_losers, length_string) 
    optimalMove = existing_Optimal_Move(FIRSTNLETTERS, first_letters_of_clear_losers) 
    if optimalMove: 
    print("OPTIMAL MOVE") 
    for item in optimalMove: 
     #print(optimalMove) 
     return item[:length_string + 1] 
    else: 
    for item in FIRSTNLETTERS: 
     #print(FIRSTNLETTERS) 
     return item[:length_string + 1] 

回答

2

退房三元搜索樹數據結構: http://en.wikipedia.org/wiki/Ternary_search_tree

你可以建立從你的單詞表三元搜索樹。然後你可以讓你的計算機循環通過樹中當前位置的孩子。他會消除任何失敗的舉動(一封信沒有孩子),然後循環所有的孩子。如果任何計算機可能的舉動都有失敗的孩子(他們自己沒有孩子),那麼他會選擇這個選擇,因爲它保證了勝利。

通過循環他將消除任何保證損失的舉措。如果他沒有剩下的動作,這意味着一舉一動都會讓他輸,所以他只會選擇隨機字母,直到他輸了。否則,他會選擇最可能失敗的方式,或者他可以贏得的最多方式,可能是實驗確定的常數的線性組合。您將需要巧妙的循環或遞歸函數。

最後如果你想讓他使用機器學習,你可能希望有一本詞典,例如memory = {},然後每次他玩和失去時他會添加他的選擇列表到內存中,並在下次避免該模式。他也可以這樣調整常量。爲了保持內存,你應該將它保存到一個文件中,或者使用python的pickle模塊對它進行序列化。

+0

謝謝喬爾。這正是我所期待的! – user7186

+0

如果遇到問題,請留言。 :) –

+0

fyi我剛剛在上面添加了我的代碼,似乎基本上做的伎倆。我看了一大堆Tree實現(非常有幫助,感謝您的建議!)。我發現直覺很有幫助,但是我最終發現自己編寫的這樣一個簡短的函數具有相當的「搜索」和「遍歷」操作似乎可以做到這一點。再次感謝! – user7186