2

Pythonでソケットリッスンするアプリケーションを作っています。私はcanonicalでQuicklyを使用しました(gi.repositoryでgladeを使用してguiを作成します)。しかし、とにかくリスニング機能へのスレッドを作成できません。thread クラスと threading.Thread クラスでも多くの方法を試しました。私はQuicklyとスレッドがまったく初めてです。私はインターネットですべてを試しました:-)しかし、解決策が見つかりません。thread.start() を使用すると、GUI が閉じるまで待機します。thread.run() を使用すると、GUI から抜け出し、すぐに関数を実行して、GUI が応答しなくなります。以下は、スレッドクラスに使用したサンプルコードです。これはオープン ソース プロジェクトであるため、必要に応じてファイル全体をアップロードできます。私を助けてください。

def listen(self):
    print "working"
#listen to any incoming connections
    #self.control_sock_in.listen(1)
    i=0
    while True:
        print "it works"
    #conn,addr = self.control_sock_in.accept()
    #data = conn.recv
    #if there is any incoming connection then check for free slot and reply with that free slot
#if change of status message then update nodelist

def on_btn_create_n_clicked(self, widget):
    self.btn_quit_n.set_sensitive(True)
    self.btn_join_n.set_sensitive(False)
    self.btn_create_n.set_sensitive(False)
    subprocess.check_call(["sudo", "ifconfig", "wlan0", "192.168.0.5", "netmask", "255.255.255.0", "broadcast", "192.168.0.255"])
    self.control_sock_in = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    self.control_sock_in.bind(('192.168.0.5', 6000))
    self.status_lbl.set_text("Created the network successfully with IP of 192.168.0.5!")
    self.nodelist['192.168.0.5'] = ('6000','0')
#start thread on listen()  
    thread.start_new_thread(self.listen,(self,))
    self.btn_camera.set_sensitive(True)
    self.btn_mixer.set_sensitive(True)
    self.btn_display.set_sensitive(True)

ところで、コメントされたアイテムの不足しているコードを提供する必要はありません。私はそれらを行うことができます。私が立ち往生しているのは、スレッドの問題です。

4

2 に答える 2

2

あなたはそれと同じくらい簡単にそれを行うことができます

from threading import Thread
listener_thread = Thread(target=self.listen)
listener_thread.start()

プログラムが終了し、デーモン以外のスレッドが実行されている場合、それらがすべて終了するまで待機します。

スレッドにdaemonとしてフラグを立てることができますが、注意が必要です。詳細については、この記事を参照してください。基本的に、他のスレッドでクリーンアップが行われているか、すでに行われているため、一貫した状態のデータを使用してまだ実行されている可能性があります。

デーモン スレッドの作成:

from threading import Thread
listener_thread = Thread(target=self.listen)
listener_thread.daemon = True 
# or listener_thread.setDaemon(True) for old versions of python
listener_thread.start()

最良のオプションは、リスナー スレッドを非デーモン (デフォルト) のままにし、プログラムが終了しようとしているときにリスナー スレッドに何らかの方法で通知する方法を考えることです。したがって、リスナー スレッドを正常に終了できます。

更新しました

runスレッドのオブジェクトのメソッドを使用しないでください。現在呼び出しているスレッドで指定した関数を呼び出すだけです。startオブジェクトのメソッドを呼び出すThreadと、別のスレッドでアクティビティが開始されます。

于 2012-12-04T11:46:28.350 に答える
0

さて、ここで解決策を見つけました。askubuntu からのリンク この 2 行を先頭に追加する必要が ありfrom gi.repository import GObject, Gtk GObject.threads_init()ます。

とにかく、問題を指摘してくれた IRC チャンネルの Michael Hall に大いに感謝します。

于 2012-12-07T15:42:18.600 に答える