可以我让一个线程结束主 Python 脚本。

huangapple go评论63阅读模式
英文:

Can I make a thread end the main python script

问题

I have written an email forwarding program. I want to incorporate an emergency stop key that will raise an exception in the main script. I tried "raise Exception" and "sys.exit(1)" however it seems to end the thread rather than the main script.

My code:

import pyautogui as key
import keyboard as kb
import time
import threading

# Thread

def CheckPress():
    while 1:
        if kb.is_pressed("esc"):
            raise Exception  # End Program if "esc" is pressed
            break
        else:
            time.sleep(0.1)

checkThread = threading.Thread(target=CheckPress)
checkThread.start()

# My Main Code
NumberOfEmails = 100  # How many emails to send
for count in range(NumberOfEmails):
    # gmail forward hotkey
    key.press("f")
    time.sleep(1)

    # type email
    key.write("email@gmail.com", interval=0.05)
    time.sleep(1)

    # send email
    key.hotkey("ctrl", "Enter")
    time.sleep(1)

    # move to the next email
    key.hotkey("j")
    time.sleep(1)

Is it possible for a thread to end the main script? If so, how can I go about it.

Thanks!

英文:

I have written an email forwarding program. I want to incorporate an emergency stop key that will raise an exception in the main script. I tried "raise Exception" and "sys.exit(1)" however it seems to end the thread rather than the main script.

My code:

import pyautogui as key
import keyboard as kb
import time
import threading

# Thread


def CheckPress():
    while 1:
        if kb.is_pressed("esc"):
            raise Exception  # End Program of "esc" is pressed
            break
        else:
            time.sleep(0.1)


checkThread = threading.Thread(target=CheckPress)
checkThread.start()

# My Main Code
NumberOfEmails = 100  # How many emails to send
for count in range(NumberOfEmails):
    # gmail forward hotkey
    key.press("f")
    time.sleep(1)

    # type email
    key.write("email@gmail.com", interval=0.05)
    time.sleep(1)

    # send email
    key.hotkey("ctrl", "Enter")
    time.sleep(1)

    # move to next email
    key.hotkey("j")
    time.sleep(1)

Is it possible for a thread to end the main script? If so, how can I go about it.

Thanks!

答案1

得分: 1

以下是您要翻译的内容:

Referencing https://stackoverflow.com/questions/29892984/how-do-i-terminate-parent-thread-from-child. It is never a good idea to terminate a thread from outside that thread. Instead, you should send a signal to the other thread and that thread exits itself as mentioned in Method 1.

There is another way, Referencing https://stackoverflow.com/questions/905189/why-does-sys-exit-not-exit-when-called-inside-a-thread-in-python. This is basically same as closing your program through KeyboardInterrupt (CTRL + C). I don't recommend it but you can follow Method 2 in order to use that.

Method 1 (Proper Way) :

We can use threading.Event object. The event is set inside the child thread and then checked in the main thread if it is activated, the main program is break out of its loop or you can call exception based on that in you main program.

import pyautogui as key
import keyboard as kb
import time
import threading

# Thread

exit_signal = threading.Event()  # your global exit signal

def CheckPress():
    while 1:
        if kb.is_pressed("esc"):
            exit_signal.set()
            break
        else:
            time.sleep(0.1)

checkThread = threading.Thread(target=CheckPress)
checkThread.start()

# My Main Code
NumberOfEmails = 100  # How many emails to send
for count in range(NumberOfEmails):
    if exit_signal.is_set():
        # break out of main loop so main program would automatically close.
        break
    else:
        # gmail forward hotkey
        key.press("f")
        time.sleep(1)

        # type email
        key.write("email@gmail.com", interval=0.05)
        time.sleep(1)

        # send email
        key.hotkey("ctrl", "Enter")
        time.sleep(1)

        # move to next email
        key.hotkey("j")
        time.sleep(1)

Method 2 :

Assuming you are using Linux, use the code below otherwise use os._exit instead of os.kill(os.getpid(), signal.SIGINT).

import pyautogui as key
import keyboard as kb
import time
import threading
import signal
import os

# Thread

def CheckPress():
    while 1:
        if kb.is_pressed("esc"):
            break
        else:
            time.sleep(0.1)
    os.kill(os.getpid(), signal.SIGINT)

checkThread = threading.Thread(target=CheckPress)
checkThread.start()

# My Main Code
NumberOfEmails = 100  # How many emails to send
for count in range(NumberOfEmails):
    # gmail forward hotkey
    key.press("f")
    time.sleep(1)

    # type email
    key.write("email@gmail.com", interval=0.05)
    time.sleep(1)

    # send email
    key.hotkey("ctrl", "Enter")
    time.sleep(1)

    # move to next email
    key.hotkey("j")
    time.sleep(1)
英文:

Referencing https://stackoverflow.com/questions/29892984/how-do-i-terminate-parent-thread-from-child. It is never a good idea to terminate a thread from outside that thread. Instead, you should send a signal to the other thread and that thread exits itself as mentioned in Method 1.

There is another way, Referencing https://stackoverflow.com/questions/905189/why-does-sys-exit-not-exit-when-called-inside-a-thread-in-python. This is basically same as closing your program through KeyboardInterrupt (CTRL + C). I don't recommend it but you can follow Method 2 in order to use that.

Method 1 (Proper Way) :

We can use threading.Event object. The event is set inside the child thread and then checked in the main thread if it is activated, the main program is break out of its loop or you can call exception based on that in you main program.

import pyautogui as key
import keyboard as kb
import time
import threading

# Thread

exit_signal = threading.Event()  # your global exit signal


def CheckPress():
    while 1:
        if kb.is_pressed("esc"):
            exit_signal.set()
            break
        else:
            time.sleep(0.1)

checkThread = threading.Thread(target=CheckPress)
checkThread.start()


# My Main Code
NumberOfEmails = 100  # How many emails to send
for count in range(NumberOfEmails):
    if exit_signal.is_set():
        # break out of main loop so main program would automatically close.
        break
    else:
        # gmail forward hotkey
        key.press("f")
        time.sleep(1)

        # type email
        key.write("email@gmail.com", interval=0.05)
        time.sleep(1)

        # send email
        key.hotkey("ctrl", "Enter")
        time.sleep(1)

        # move to next email
        key.hotkey("j")
        time.sleep(1)

Method 2 :

Assuming you are using Linux, use the code below otherwise use os._exit instead of os.kill(os.getpid(), signal.SIGINT).

import pyautogui as key
import keyboard as kb
import time
import threading
import signal
import os

# Thread


def CheckPress():
    while 1:
        if kb.is_pressed("esc"):
            break
        else:
            time.sleep(0.1)
    os.kill(os.getpid(), signal.SIGINT)

checkThread = threading.Thread(target=CheckPress)
checkThread.start()


# My Main Code
NumberOfEmails = 100  # How many emails to send
for count in range(NumberOfEmails):
    # gmail forward hotkey
    key.press("f")
    time.sleep(1)

    # type email
    key.write("email@gmail.com", interval=0.05)
    time.sleep(1)

    # send email
    key.hotkey("ctrl", "Enter")
    time.sleep(1)

    # move to next email
    key.hotkey("j")
    time.sleep(1)

huangapple
  • 本文由 发表于 2023年6月6日 09:59:38
  • 转载请务必保留本文链接:https://go.coder-hub.com/76410977.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定