2015-07-20 393 views
0

的PID這是一個後續問題到先前的(再次發表我):PyQt4 QProcess state always 0, various slots not working tooPyQt4的QProcess.startDetached() - 不能獲得返回值和衍生的過程

代碼(修改):

主要應用:qprocess_test.py

#!/usr/bin/python 

import sys 
from PyQt4 import QtGui, QtCore 
from PyQt4.QtCore import QProcess 


class Example(QtGui.QWidget): 


    def __init__(self): 
     super(Example, self).__init__() 
     self.command = "./testCommand.py" 
     self.args = [""] 
     self.initUI() 

    def initUI(self):    
     hbox = QtGui.QHBoxLayout() 
     hbox.addStretch(1) 

     qbtn = QtGui.QPushButton('Start', self) 
     qbtn.clicked.connect(self.toggleProcess) 
     qbtn.resize(qbtn.sizeHint()) 
     hbox.addWidget(qbtn) 

     # This button is for testing the responsiveness of the GUI after the QProcess has been started 
     qbtn2 = QtGui.QPushButton('Click me', self) 
     qbtn2.setCheckable(True) 
     qbtn2.toggled.connect(self.toggleButton) 
     qbtn2.resize(qbtn2.sizeHint()) 
     hbox.addWidget(qbtn2) 

     self.setLayout(hbox) 
     self.setGeometry(300, 300, 250, 150) 
     self.setWindowTitle('QProcess controlled by a button')  
     self.show() 

    def toggleProcess(self): 
     res, pid = QProcess.startDetached(self.command, self.args) 
      print "Starting process\n", str(res), " | pid = ", str(pid) 

    def toggleButton(self, value): 
     if value == True: 
      print "Lalalala!" 
     else: 
      print "Didadida!" 

def main(): 
    app = QtGui.QApplication(sys.argv) 
    ex = Example() 
    sys.exit(app.exec_()) 


if __name__ == '__main__': 
    main() 

現在所有開始按鈕不會是啓動分離的進程。這個想法是可以切換的,並且當用戶根據PID與它交互時停止/啓動分離的進程。

用於創建過程中的應用:我發現該startDetached()函數在Python返回2倍的值(在C testCommand.py

#!/usr/bin/env python 

while True: 
    print "a" 

做一些閱讀和谷歌搜索後++它是一個布爾函數,但它也將它的一個參數的值 - 指針PID):

  • 布爾:告訴我們如果分離的進程的開始是成功還是失敗
  • INT:給人的啓動進程的PID,如果操作成功

以下是我已經使用這個信息來源:

由於某種原因,這根本不起作用。以下是我已經測試了兩種情況:

  • 試圖從功能同時獲得BOOL和INT值:

    res, pid = self.myProcess.startDetached(self.command, self.args) 
    

    我得到這個錯誤:

    Traceback (most recent call last): 
        File "./qprocess_test.py", line 48, in toggleProcess 
        res, pid = self.myProcess.startDetached(self.command, self.args) 
    TypeError: 'bool' object is not iterable 
    

    這告訴我,我無法迭代startDetached()的返回值,因此只有一個SINGLE值實際返回,而不是兩個,因爲我也在multipl中看到過Ë件代碼PyQt4的文檔的一部分再次...

  • 檢查什麼startDetached()實際上返回:現在看來,這只是返回一個int,這我相信是PID。但是,如果它是不正確的值的PID(看HTOP的輸出):

    val = QProcess.startDetached(self.command, self.args) 
    # val = 0 (always!) 
    

我已經瞭解到,startDetached()是靜態函數,因此與未來互動創建的過程可以通過它的pid來完成,但是像調用它的狀態(QProcess.state())等等是不可能的,因爲沒有對象可以與之交互。現在這種(破碎的)工作的方式確實開始了一個分離的過程,但由於我沒有任何識別它的PID,因此我唯一的交互方式是手動找到testCommand.py的PID,然後通過執行相應的信號kill

有沒有人知道我在做什麼錯在這裏?我可以去基礎知識,並開始使用C/C++與各種系統調用,但我真的很想學習如何使用PyQt4和Python做到這一點。

謝謝!

編輯

似乎startDetached()確實返回TRUE | FALSE。然而,PID無處可尋......不是官方文件中的內容。

+0

爲了您的第二種情況:我認爲int值'startDetached()'返回的是布爾值,而不是PID(0 =假1 =真) – Mel

+2

根據PyQt Doc,返回PID的實際函數是'(bool,int pid)QProcess.startDetached(QString程序,QStringList參數,QString workingDirectory)'。請注意第三個參數。 – Mel

+0

Qt文檔還指出,如果沒有給出workingDirectory,則啓動的進程將從產卵進程獲取值。順便說一句我也嘗試從這個函數中獲取一個元組(通過添加圓括號) - 與bool不可迭代相同的錯誤。 – rbaleksandar

回答

2

函數startDetached在C++中被重載,它有幾個簽名。根據提供的參數,它並不需要返回相同的東西。

即使overloading does not exist in Python,你有類似的東西:

import sys 
from PyQt4 import QtGui, QtCore 
from PyQt4.QtCore import QProcess 

if __name__ == '__main__': 
    app = QtGui.QApplication(sys.argv) 

    command = "./testCommand.py" 
    args = [""] 

    #"regular" startDetached : give two arguments, get a boolean 
    process=QProcess() 
    re=process.startDetached("ls",["."]) 
    print(re) 
    print(type(re)) 

    #"overload" startDetached : give three arguments, get a tuple(boolean,PID) 
    process2=QProcess() 
    re,pid=process2.startDetached("ls",["."],".") 
    print(re,pid) 
    print(type(re),type(pid)) 
+0

再次感謝一堆!順便說一下,由於startDetached()的性質,您不需要過程變量。它工作得很好。此外,我真的必須從頭開始閱讀文檔--PyQt4文檔明確描述了QProcess.startDetached()的所有3個版本以及那些返回的內容...... -_- – rbaleksandar