我正在监视一个外部设备,当不满足条件时,它输出一个布尔值False,当满足条件时,它输出一个布尔值True。 问题是,在满足条件后,布尔值会多次输出。
这是输出的样子:
False
False
False
False
True
True
False
False
False
所以我希望能够做的是监视这个值并执行一个简单的函数,每次布尔值从False变为True时只执行一次。我见过其他语言有一个简单的变化"功能,所以我知道它可能,并且可能比我做得更容易。
目前我有这个。为了解释这个,变量" ext_data"用作python脚本正在监视的外部数据。
while True:
if ext_data == True:
print("true")
pass
这打印" true"每次布尔值等于true时,当它重置自身时,布尔值仍然设置为True,所以当我只想要一个时,我得到多个读数。
感谢任何帮助过的人!
编辑:
使用holdenweb编写的EdgeDetector类更新了代码。
ext_data = True/False # This returns True or False depending on the state
# of the variable. It is constantly monitored and
# could change at any moment, which is why I'm
# running the function in a while True loop
def printer():
print(u'something%s' % serialport.cts)
post_to_api('cycle_count')
def myfunction():
return ext_data
test_subject = EdgeDetector(myfunction, printer)
while True:
test_subject.test()
这仍然会偶尔返回重复的帖子。有人提到这个数据需要在一个数组中才能使EdgeDetector Class正常工作,你如何建议将这些数据放入一个数组而不创建一个无限长的数组呢?
答案 0 :(得分:2)
您的问题框架的方式并不清楚如何获得外部价值。这必须涉及存储状态信息 - 特别是最后读取的值。
虽然可以将它存储在全局变量中,但这不是一个好的做法 - 虽然它可以满足您的直接需求,但如果您尝试基于它创建一个可重用的软件组件,它将会破坏事件,同一模块中的某些其他代码决定将相同的全局变量用于其他目的。所以课程可能会更令人满意。
编写以下类来接收一个函数,该函数在被调用时返回外部变量的值。这将作为参数__init__
传递给班级read_signal
。第二个参数action
是对象在检测到False
到True
转换时应调用的函数。
以这种形式投射它意味着你可以轻松地将它集成到任何程序中,如果你自己不得不处理许多外部变量,你可以为每个变量创建一个EdgeDetector
。
class EdgeDetector:
"""Detects False to True transitions on an external signal."""
def __init__(self, reader, action):
self.reader = reader
self.action = action
self.last_value = reader() # initialise value
def test(self):
new_value = self.reader()
if new_value and not self.last_value:
self.action()
self.last_value = new_value
if __name__ == '__main__': # simple self-test
vlist = [False, False, False, True, True, False, True, True, False, False, False, True]
vgen = (v for v in vlist) # generator for value sequence
def test_reader(): # generate test sequence
value = next(vgen)
print("Read:", value)
return value
def printer():
print("Edge transition detected")
test_subject = EdgeDetector(test_reader, printer)
for i in range(len(vlist)-1):
test_subject.test()
通常,您可以将此模块导入到您的程序中,从而可以更轻松地重复使用,并使实现细节远离主代码。当作为程序运行时,自检代码会显示输入值的序列以及检测到转换的时间,从而使您在部署代码之前对代码更有信心。自检的输出是
Read: False
Read: False
Read: False
Read: True
Edge transition detected
Read: True
Read: False
Read: True
Edge transition detected
Read: True
Read: False
Read: False
Read: False
Read: True
Edge transition detected
答案 1 :(得分:1)
你可以有一个你跟踪的内部变量(伪代码)
executed = false
if(!executed && output_from_device == true)
print("true")
executed = true
但是我不知道你的整个设置,所以为它创建某种形式的事件处理可能更好,而不是一种天真的方法。
答案 2 :(得分:1)
为什么不简单地说:
#Input Boolean
inputData = [True,False,False,False,True,True,False]
foo =''
for i in inputData:
if foo != i:
print("Yo")
foo = i
InputData的第一个元素将触发打印,因为foo为空,然后为foo = True,下次当inputData元素为False时触发打印...等等...