2014-03-29 40 views
2

我試圖建立一個功能,將允許重複此(它可以防止控制檯從開口窗戶):問題與等號和功能參數

if platform.system() == 'Windows': 
     startupinfo = subprocess.STARTUPINFO() 
     startupinfo.dwFlags |= subprocess.STARTF_USESHOWWINDOW 
     subprocess.call(['myprogram.exe', '-P', arg], 
         stdout=someFile, startupinfo=startupinfo) 
    else: 
     subprocess.call(['myprogram.exe', '-P', arg], stdout=someFile) 

所以我定義瞭如下功能:

def noWinConsole(program): 
    if platform.system() == 'Windows': 
     startupinfo = subprocess.STARTUPINFO() 
     startupinfo.dwFlags |= subprocess.STARTF_USESHOWWINDOW 
     subprocess.call(program, startupinfo=startupinfo) 
    else: 
     subprocess.call(program) 

但是,當我這樣稱呼它noWinConsole(['myprogram.exe', '-P', arg], stdout=someFile),我得到的,因爲stdout=somefile的錯誤:

TypeError: noWinConsole() got an unexpected keyword argument 'stdout' 

我該如何解決這個問題?

回答

3

noWinConsole只是一個包裝,它只是一個單一的參數program。因此,當您給出兩個參數(第一個位置參數爲program,然後subprocess調用的關鍵字參數爲stdout)時,它就會嚇倒。

幸運的是,有一個標準的習慣用於生成一個將任何參數集傳遞給內部函數的包裝器。它使用***表示法進行參數打包/解包。

def noWinConsole(*args, **kwargs): 
    # Other stuff here as needed 
    subprocess.call(*args, **kwargs) 

這樣做基本上是這樣的。函數定義中的*運算符將獲取所有輸入位置參數,並將它們打包到名爲args的元組中。然後當您撥打subprocess時,*運營商解包該元組,將這些相同的參數以相同的順序傳遞給下一個函數。

**運營商的工作本質上是相同的方式,但它抓住關鍵字參數像stdout='foo.txt'和包裝所有的人都到像{'stdout':'foo.txt'}字典。當您在調用內部函數時再次使用**時,會將該字典解壓縮並轉換回關鍵字參數。

+0

謝謝你的回答,我更新了更正後的代碼的問題,確實你覺得合適嗎? – yaka

+0

@ yaka好像它會適用於你的用例,是的。儘管稍後可能會對第一個參數使用單星解壓縮更清晰。另外,通常不贊成編輯一個問題的答案;它爲未來的訪客們揣測事情。所以你應該刪除它。很高興我能夠幫助! –

+0

@eryksun確實!我實際上考慮在這裏增加一個提到'partial',但是我決定反對它,因爲它與提問者確實需要回答的問題有點接近(「爲什麼Python不會自動將任意數量的參數打包到單個參數中什麼是功能簽名「)。 –

1

功能noWinConsole只希望一個參數,當你把它叫做:

noWinConsole(['myprogram.exe', '-P', arg], stdout=someFile) 

你逝去兩個參數

  • 列表
  • 關鍵字參數stdout = someFile

如何解決這個問題?

你可以這樣做兩種方式:

  • 定義你的方法來獲取kwargs。請注意,您不使用的參數stdout

    def noWinConsole(program, **kwargs): 
    
  • 調用該函數只是路過一個參數:

    noWinConsole(['myprogram.exe', '-P', arg])