AttributeError: 'NoneType' object has no attribute 'terminate'
AttributeError: 'NoneType' object has no attribute 'terminate'
我正在为玩具炸弹编写代码,可以安放和拆除。但我有一个问题。当时间达到零时,p1 进程应该终止 p2 进程,但我得到一个错误。我不明白,因为 p2 进程可以很好地停止 p1 进程。
我的全部代码:
import RPi.GPIO as GPIO
from rpi_lcd import LCD
from time import sleep
import time
from multiprocessing import Process
# RPi setup
GPIO.setmode(GPIO.BCM)
GPIO.setwarnings(False)
# Button setup
GPIO.setup(17, GPIO.IN, pull_up_down=GPIO.PUD_DOWN) # Yellow
GPIO.setup(27, GPIO.IN, pull_up_down=GPIO.PUD_DOWN) # Blue
# LCD setup
lcd = LCD()
# Keypad setup
length = 6
col = [19, 13, 6, 5]
row = [21, 20, 16, 26]
for j in range(4):
GPIO.setup(col[j], GPIO.OUT)
GPIO.output(col[j], 1)
for i in range(4):
GPIO.setup(row[i], GPIO.IN, pull_up_down=GPIO.PUD_UP)
# Password checker
def check_keypad(length):
col = [19, 13, 6, 5]
row = [21, 20, 16, 26]
matrix = [["1", "2", "3", "A"],
["4", "5", "6", "B"],
["7", "8", "9", "C"],
["*", "0", "#", "D"]]
result = ""
while True:
for j in range(4):
GPIO.output(col[j], 0)
for i in range(4):
if GPIO.input(row[i]) == 0:
time.sleep(0.02)
result = result + matrix[i][j]
print(result)
while GPIO.input(row[i]) == 0:
time.sleep(0.02)
GPIO.output(col[j], 1)
if len(result) >= length:
return result
# Start sequence
def starter():
global password
x = 0
lcd.text("Starting...", 1)
sleep(5)
lcd.clear()
lcd.text("Input a password", 1)
matrix = [["1", "2", "3", "A"],
["4", "5", "6", "B"],
["7", "8", "9", "C"],
["*", "0", "#", "D"]]
passwordmaker = ""
while x != 1:
lcd.text(passwordmaker, 2)
for j in range(4):
GPIO.output(col[j], 0)
for i in range(4):
if GPIO.input(row[i]) == 0:
time.sleep(0.02)
passwordmaker = passwordmaker + matrix[i][j]
# print(passwordmaker) # thingy
while GPIO.input(row[i]) == 0:
time.sleep(0.02)
GPIO.output(col[j], 1)
if len(passwordmaker) == 6:
lcd.text(passwordmaker, 2)
password = passwordmaker
print("Password - " + password)
x = 1
sleep(0.5)
lcd.clear()
lcd.text("Initiating", 1)
lcd.text("startup sequence", 2)
sleep(2)
lcd.clear()
sleep(0.5)
# Timer
def timer():
timeA = 41 # 40 + 1
while timeA != 0:
sleep(1)
timeA = timeA - 1
lcd.text(str(timeA), 1)
print(timeA)
p2.terminate()
lcd.clear()
lcd.text("Boom!", 1)
# Code
def code():
y1 = 3 # Amount of tries
y2 = 0
for y in range(3):
# Password from keypad
y1str = str(y1)
text = "( " + y1str + " / 3 )"
lcd.text(text, 2)
result = check_keypad(length)
y1 = y1 - 1
# Password check
if result == password:
y2 = 1
break
# Correct password
if y2 == 1:
p1.terminate()
lcd.clear()
lcd.text("Deactivated", 1)
sleep(10)
# Incorrect password
elif y1 == 0 & y2 == 0:
p1.terminate()
lcd.clear()
lcd.text("Boom!", 1)
sleep(10)
# Multiprocessing setup
p1 = Process(target=timer)
p2 = Process(target=code)
# Stuff
starter()
p1.start()
p2.start()
问题点:
def timer():
timeA = 41 # 40 + 1
while timeA != 0:
sleep(1)
timeA = timeA - 1
lcd.text(str(timeA), 1)
print(timeA)
p2.terminate()
lcd.clear()
lcd.text("Boom!", 1)
我想终止 p2 进程,但我一直收到此错误:
Process Process-1:
Traceback (most recent call last):
File "/usr/lib/python3.7/multiprocessing/process.py", line 297, in _bootstrap
self.run()
File "/usr/lib/python3.7/multiprocessing/process.py", line 99, in run
self._target(*self._args, **self._kwargs)
File "/home/pi/home/pi/Desktop/pybomb/main.py", line 115, in timer
p2.terminate()
File "/usr/lib/python3.7/multiprocessing/process.py", line 124, in terminate
self._popen.terminate()
AttributeError: 'NoneType' object has no attribute 'terminate'
我不明白为什么我一直收到那个错误,我可以在这里终止 p1 进程:
def code():
y1 = 3 # Amount of tries
y2 = 0
for y in range(3):
# Password from keypad
y1str = str(y1)
text = "( " + y1str + " / 3 )"
lcd.text(text, 2)
result = check_keypad(length)
y1 = y1 - 1
# Password check
if result == password:
y2 = 1
break
# Correct password
if y2 == 1:
p1.terminate()
lcd.clear()
lcd.text("Deactivated", 1)
sleep(10)
# Incorrect password
elif y1 == 0 & y2 == 0:
p1.terminate()
lcd.clear()
lcd.text("Boom!", 1)
sleep(10)
您可以依靠信号来终止这两个进程。在引擎盖下, Process.terminate() 方法向目标进程传递一个 SIGTERM 信号。
您需要一个 Queue 或 Pipe 来向进程发送彼此的 PID。只有父(主)进程可以这样做。在两个进程创建管道之前的主代码中。
from multiprocessing import Process, Pipe
import signal
import os
# rest of the code
# Multiprocessing setup
conn1, conn2 = Pipe()
p1 = Process(target=timer, args=(conn1,))
p2 = Process(target=code, args=(conn2,))
# Stuff
starter()
p1.start()
p2.start()
conn1.send(p2.pid)
conn2.send(p1.pid)
现在编辑您的两个函数以将管道作为参数
def timer(pipe):
p2_pid = pipe.recv()
#rest of the code
#instead of terminate use
os.kill(p2_pid, signal.SIGTERM)
def code(pipe):
p1_pid = pipe.recv()
#rest of the code
#instead of terminate use
os.kill(p1_pid, signal.SIGTERM)
我正在为玩具炸弹编写代码,可以安放和拆除。但我有一个问题。当时间达到零时,p1 进程应该终止 p2 进程,但我得到一个错误。我不明白,因为 p2 进程可以很好地停止 p1 进程。 我的全部代码:
import RPi.GPIO as GPIO
from rpi_lcd import LCD
from time import sleep
import time
from multiprocessing import Process
# RPi setup
GPIO.setmode(GPIO.BCM)
GPIO.setwarnings(False)
# Button setup
GPIO.setup(17, GPIO.IN, pull_up_down=GPIO.PUD_DOWN) # Yellow
GPIO.setup(27, GPIO.IN, pull_up_down=GPIO.PUD_DOWN) # Blue
# LCD setup
lcd = LCD()
# Keypad setup
length = 6
col = [19, 13, 6, 5]
row = [21, 20, 16, 26]
for j in range(4):
GPIO.setup(col[j], GPIO.OUT)
GPIO.output(col[j], 1)
for i in range(4):
GPIO.setup(row[i], GPIO.IN, pull_up_down=GPIO.PUD_UP)
# Password checker
def check_keypad(length):
col = [19, 13, 6, 5]
row = [21, 20, 16, 26]
matrix = [["1", "2", "3", "A"],
["4", "5", "6", "B"],
["7", "8", "9", "C"],
["*", "0", "#", "D"]]
result = ""
while True:
for j in range(4):
GPIO.output(col[j], 0)
for i in range(4):
if GPIO.input(row[i]) == 0:
time.sleep(0.02)
result = result + matrix[i][j]
print(result)
while GPIO.input(row[i]) == 0:
time.sleep(0.02)
GPIO.output(col[j], 1)
if len(result) >= length:
return result
# Start sequence
def starter():
global password
x = 0
lcd.text("Starting...", 1)
sleep(5)
lcd.clear()
lcd.text("Input a password", 1)
matrix = [["1", "2", "3", "A"],
["4", "5", "6", "B"],
["7", "8", "9", "C"],
["*", "0", "#", "D"]]
passwordmaker = ""
while x != 1:
lcd.text(passwordmaker, 2)
for j in range(4):
GPIO.output(col[j], 0)
for i in range(4):
if GPIO.input(row[i]) == 0:
time.sleep(0.02)
passwordmaker = passwordmaker + matrix[i][j]
# print(passwordmaker) # thingy
while GPIO.input(row[i]) == 0:
time.sleep(0.02)
GPIO.output(col[j], 1)
if len(passwordmaker) == 6:
lcd.text(passwordmaker, 2)
password = passwordmaker
print("Password - " + password)
x = 1
sleep(0.5)
lcd.clear()
lcd.text("Initiating", 1)
lcd.text("startup sequence", 2)
sleep(2)
lcd.clear()
sleep(0.5)
# Timer
def timer():
timeA = 41 # 40 + 1
while timeA != 0:
sleep(1)
timeA = timeA - 1
lcd.text(str(timeA), 1)
print(timeA)
p2.terminate()
lcd.clear()
lcd.text("Boom!", 1)
# Code
def code():
y1 = 3 # Amount of tries
y2 = 0
for y in range(3):
# Password from keypad
y1str = str(y1)
text = "( " + y1str + " / 3 )"
lcd.text(text, 2)
result = check_keypad(length)
y1 = y1 - 1
# Password check
if result == password:
y2 = 1
break
# Correct password
if y2 == 1:
p1.terminate()
lcd.clear()
lcd.text("Deactivated", 1)
sleep(10)
# Incorrect password
elif y1 == 0 & y2 == 0:
p1.terminate()
lcd.clear()
lcd.text("Boom!", 1)
sleep(10)
# Multiprocessing setup
p1 = Process(target=timer)
p2 = Process(target=code)
# Stuff
starter()
p1.start()
p2.start()
问题点:
def timer():
timeA = 41 # 40 + 1
while timeA != 0:
sleep(1)
timeA = timeA - 1
lcd.text(str(timeA), 1)
print(timeA)
p2.terminate()
lcd.clear()
lcd.text("Boom!", 1)
我想终止 p2 进程,但我一直收到此错误:
Process Process-1:
Traceback (most recent call last):
File "/usr/lib/python3.7/multiprocessing/process.py", line 297, in _bootstrap
self.run()
File "/usr/lib/python3.7/multiprocessing/process.py", line 99, in run
self._target(*self._args, **self._kwargs)
File "/home/pi/home/pi/Desktop/pybomb/main.py", line 115, in timer
p2.terminate()
File "/usr/lib/python3.7/multiprocessing/process.py", line 124, in terminate
self._popen.terminate()
AttributeError: 'NoneType' object has no attribute 'terminate'
我不明白为什么我一直收到那个错误,我可以在这里终止 p1 进程:
def code():
y1 = 3 # Amount of tries
y2 = 0
for y in range(3):
# Password from keypad
y1str = str(y1)
text = "( " + y1str + " / 3 )"
lcd.text(text, 2)
result = check_keypad(length)
y1 = y1 - 1
# Password check
if result == password:
y2 = 1
break
# Correct password
if y2 == 1:
p1.terminate()
lcd.clear()
lcd.text("Deactivated", 1)
sleep(10)
# Incorrect password
elif y1 == 0 & y2 == 0:
p1.terminate()
lcd.clear()
lcd.text("Boom!", 1)
sleep(10)
您可以依靠信号来终止这两个进程。在引擎盖下, Process.terminate() 方法向目标进程传递一个 SIGTERM 信号。 您需要一个 Queue 或 Pipe 来向进程发送彼此的 PID。只有父(主)进程可以这样做。在两个进程创建管道之前的主代码中。
from multiprocessing import Process, Pipe
import signal
import os
# rest of the code
# Multiprocessing setup
conn1, conn2 = Pipe()
p1 = Process(target=timer, args=(conn1,))
p2 = Process(target=code, args=(conn2,))
# Stuff
starter()
p1.start()
p2.start()
conn1.send(p2.pid)
conn2.send(p1.pid)
现在编辑您的两个函数以将管道作为参数
def timer(pipe):
p2_pid = pipe.recv()
#rest of the code
#instead of terminate use
os.kill(p2_pid, signal.SIGTERM)
def code(pipe):
p1_pid = pipe.recv()
#rest of the code
#instead of terminate use
os.kill(p1_pid, signal.SIGTERM)