2017-06-01 71 views
1

當使用字典值時嘗試創建字符串時出現奇怪的問題。基本上,我有一個函數打開文件,讀取一行,並將它在該行中找到的值存儲在字典中。然後,它將這些值發送到外部程序。下面是代碼:使用字典值時的字符串格式問題

def createLandscapes(file): 

    landscapeParameters = {'FILE': "NULL", 
         'N': "NULL", 
         'K': "NULL", 
         'NUM': "100"} 

    for line in file: 
    if line == "END LANDSCAPES\n": 
     break 
    else: 
     parameters = line.replace(" ", '').split(",") 

     for parameter in parameters: 
     parameter = parameter.split("=") 
     if parameter[0] not in landscapeParameters: 
      malformedFile() 
     landscapeParameters[parameter[0]] = parameter[1] 

     for key in landscapeParameters: 
     if landscapeParameters[key] == "NULL": 
      malformedFile() 

     # This print statment is for diagnostic purposes 
     print("./generateScoreTables {} {} {} {}".format(landscapeParameters['FILE'], 
                 landscapeParameters['N'], 
                 landscapeParameters['K'], 
                 landscapeParameters['NUM'])) 

     os.system("./generateScoreTables {} {} {} {}".format(landscapeParameters['FILE'], 
                  landscapeParameters['N'], 
                  landscapeParameters['K'], 
                  landscapeParameters['NUM'])) 

爲了使這個很清楚,該功能會查找單一系列的參數輸入,逗號分隔線,在

FILE=example, N=20, K=5, NUM=100 

形式它需要這些輸入並覆蓋landscapeParameters中的默認輸入(如果指定),並使用landscapeParameters中的值調用外部程序。

奇怪的是,當我使用landscapeParameters中的默認參數時,字符串格式似乎不能正常工作。我的意思是,如果函數讀取行:

FILE=example, N=20, K=5, NUM=100 

一切正常,並且打印語句打印:

./generateScoreTables example 20 5 100 

但是,如果函數讀取行:

FILE=example, N=20, K=5 

我在哪裏離開NUM出來使用默認參數,我得到以下輸出:

./generateScoreTables testland1 15 
0 100 
Segmentation fault 
sh: 2: 0: not found 

它似乎格式不正確格式化此字符串,但我不明白爲什麼。有沒有人對此有所瞭解?

+4

歡迎來到StackOverflow。請閱讀並遵守幫助文檔中的發佈準則。 [最小,完整,可驗證的示例](http://stackoverflow.com/help/mcve)適用於此處。在發佈您的MCVE代碼並準確描述問題之前,我們無法爲您提供有效的幫助。 我們應該能夠將發佈的代碼粘貼到文本文件中,並重現您描述的問題。 – Prune

+0

@Prune你想補充什麼?這個問題應該是顯而易見的,並且容易從所提供的信息中重現。 – user1105224

+1

附上產生錯誤的演示輸入文件 - 可能只有兩行。將您的代碼編輯爲將重現錯誤的*最小*代碼。也許它不過是一個單線電話。 – Prune

回答

-1

您正在更新每個循環中的相同變量,因此如果它讀取一行沒有特定字段的行,它將使用上次讀取它的值。

取而代之的是在循環中聲明一個空字典,並且如果該字典中不存在該鍵,則使用.get函數來獲得默認值。

def createLandscapes(file): 
    params = ['FILE','N','K','NUM'] 

    for line in file: 
     if line == "END LANDSCAPES\n": 
      break 
     else: 
      landscapeParameters = {} 
      parameters = line.replace(" ", '').split(",") 

      for parameter in parameters: 
       parameter = parameter.split("=") 
       if parameter[0] not in params: 
        malformedFile() 
       landscapeParameters[parameter[0]] = parameter[1] 

       for key in landscapeParameters: 
       if landscapeParameters[key] == "NULL": 
        malformedFile() 
     os.system("./generateScoreTables {} {} {} {}".format(landscapeParameters.get('FILE',''), 
                  landscapeParameters.get('N',''), 
                  landscapeParameters.get('K',''), 
                  landscapeParameters.get('NUM',100))) 

您可能需要調整這一點,但它應該給你更可預測的結果。

+0

我剛剛嘗試過這一點,但我仍然以所描述的相同結果結束。 – user1105224

2

這個問題已經指出,但我仍然無法發表評論,所以我會離開這個單獨的。這將涉及到一點點修改你的代碼。

一旦進入這個階段:

parameters = ['FILE=example', 'N=20', 'K=5', 'NUM=100'] 

# make a list of tuples with [(FILE, default), ('N', 20)...] 
pars = [x.split("=") for x in parameters] 

現在將每個twople成鍵,值對字典中的dict_of_pars

dict_of_pars = {k: v for k, v in pars} 
#dictionary with values for a single line 
# {'FILE': 'example', 'N': '20', 'K': '5', 'NUM': '100'} 

此時會有一個包含所有定義的字典你任何特定線路的參數。如果你犯了一個函數(輸出),它保存的默認值,您可以發送可用參數,使用線**呼叫dict_of_pars

# define output function with default parameters 
def output(FILE='example, N='n', K='k', NUM='num'): 
     os.system(FILE, N, K, NUM) 

現在,可以調用使用功能

output(**dict_of_pars) #will unpack the arguments into output function 

爲文件中的每一行製作其中一個臨時詞典,並將其傳遞給輸出。希望這可以幫助。

+0

當然,我明白你的意思。但是你有沒有理解爲什麼字符串格式不能像我的問題中描述的那樣工作?我試着在每個循環中實現一個新的字典,以防止可能的假值(儘管這不應該是一個問題,因爲我只在一個輸入行上運行代碼),但我仍然以錯誤的字符串格式結束。除了格式化字典中的字符串值之外,必須編寫一個額外的函數,這似乎相當複雜。 – user1105224

+0

我剛剛通過了一個很好的看,無法找到你的問題,它打印正確。只要您在'for line in'語句後面定義字典,代碼就應該按預期運行。其他然後,我忍不住,對不起。 – Rosh

+0

感謝您的嘗試。實際上,我已經將自己的範圍縮小到了我確信自己已經運行了Python中的一個bug。這對我的程序來說並不重要,我現在沒有時間處理它,所以我剛剛放棄了它並使用了另一個實現。 – user1105224