我目前有 2 个按钮连接到我的 Raspberry Pi(这些是带有环形 LED 的按钮),我正在尝试执行此代码
#!/usr/bin/env python
import RPi.GPIO as GPIO
import time
GPIO.setmode(GPIO.BCM)
GPIO.setwarnings(False)
GPIO.setup(17, GPIO.OUT) #green LED
GPIO.setup(18, GPIO.OUT) #red LED
GPIO.setup(4, GPIO.IN, GPIO.PUD_UP) #green button
GPIO.setup(27, GPIO.IN, GPIO.PUD_UP) #red button
def remove_events():
GPIO.remove_event_detect(4)
GPIO.remove_event_detect(27)
def add_events():
GPIO.add_event_detect(4, GPIO.FALLING, callback=green, bouncetime=800)
GPIO.add_event_detect(27, GPIO.FALLING, callback=red, bouncetime=800)
def red(pin):
remove_events()
GPIO.output(17, GPIO.LOW)
print "red pushed"
time.sleep(2)
GPIO.output(17, GPIO.HIGH)
add_events()
def green(pin):
remove_events()
GPIO.output(18, GPIO.LOW)
print "green pushed"
time.sleep(2)
GPIO.output(18, GPIO.HIGH)
add_events()
def main():
while True:
print "waiting"
time.sleep(0.5)
GPIO.output(17, GPIO.HIGH)
GPIO.output(18, GPIO.HIGH)
GPIO.add_event_detect(4, GPIO.FALLING, callback=green, bouncetime=800)
GPIO.add_event_detect(27, GPIO.FALLING, callback=red, bouncetime=800)
if __name__ == "__main__":
main()
最佳答案
通过运行您的脚本并在接地和 GPIO27 之间连接跳线以模拟红色按钮按下,我能够在我的 Raspberry Pi 1 B 型上重现您的问题。 (这些是我的特定 Pi 型号上的引脚 25 和 13。)
在 red 之后,python 解释器因专用于轮询 GPIO 事件的线程中的段错误而崩溃。从处理按钮按下返回。看了Python的实现后GPIO模块,我很清楚调用 remove_event_detect 是不安全的从事件处理程序回调中,这会导致崩溃。特别是,在事件处理程序当前运行时删除该事件处理程序会导致内存损坏,这将导致崩溃(如您所见)或其他奇怪的行为。
我怀疑您正在删除并重新添加事件处理程序,因为您担心在按下按钮时会收到回调。没有必要这样做。 GPIO 模块启动一个轮询线程来监控 GPIO 事件,并且会等待一个回调返回,然后再调用另一个,而不管您正在观看的 GPIO 事件数量如何。
我建议您直接调用 add_event_detect当您的脚本启动时,永远不要删除回调。只需移除 add_events和 remove_events (和他们的调用)来自您的脚本将更正问题。
如果您对GPIO中的问题的详细信息感兴趣模块,你可以看看C source code for that module .看看run_callbacks和 remove_callbacks在文件中 RPi.GPIO-0.6.2/source/event_gpio.c .请注意,这两个函数都使用了 struct callback 的全局链。节点。 run_callbacks通过抓取一个节点,调用回调,然后跟随该节点的链接到链中的下一个回调来遍历回调链。 remove_callbacks将遍历相同的回调链,并释放与特定 GPIO 引脚上的回调关联的内存。如 remove_callbacks在run_callbacks中间被调用,当前持有的节点run_callbacks可以在指向下一个节点的指针之前被释放(并使其内存可能被重用和覆盖)。
您只看到红色按钮出现此问题的原因可能是由于对 add_event_detect 的调用顺序所致。和 remove_event_detect导致之前由回调节点用于红色按钮的内存被回收用于其他目的,并在绿色按钮回调节点使用的内存被类似地回收之前被覆盖。但是,请放心,这两个按钮都存在问题——幸运的是,在跟随指向下一个回调节点的指针之前,与绿色按钮回调关联的内存没有改变。
更一般地说,一般而言,GPIO 模块中使用的回调链缺乏线程同步,我怀疑如果 remove_event_detect 可能会发生类似的问题。或 add_event_detect在事件处理程序运行时调用,即使事件从另一个线程中删除!我建议作者RPi.GPIO模块应该使用一些同步来确保在进行回调时不能修改回调链。 (也许,除了检查轮询线程本身是否正在修改链之外,pthread_mutex_lock 和 pthread_mutex_unlock 可用于防止其他线程在轮询线程正在使用回调链时对其进行修改。)
不幸的是,目前情况并非如此,因此我建议您避免调用 remove_event_detect完全可以避免的话。
关于Python 按钮的功能奇怪地不一样,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39785577/
关闭。这个问题是opinion-based.它目前不接受答案。想要改进这个问题?更新问题,以便editingthispost可以用事实和引用来回答它.关闭4年前。Improvethisquestion我想在固定时间创建一系列低音和高音调的哔哔声。例如:在150毫秒时发出高音调的蜂鸣声在151毫秒时发出低音调的蜂鸣声200毫秒时发出低音调的蜂鸣声250毫秒的高音调蜂鸣声有没有办法在Ruby或Python中做到这一点?我真的不在乎输出编码是什么(.wav、.mp3、.ogg等等),但我确实想创建一个输出文件。
只是想确保我理解了事情。据我目前收集到的信息,Cucumber只是一个“包装器”,或者是一种通过将事物分类为功能和步骤来组织测试的好方法,其中实际的单元测试处于步骤阶段。它允许您根据事物的工作方式组织您的测试。对吗? 最佳答案 有点。它是一种组织测试的方式,但不仅如此。它的行为就像最初的Rails集成测试一样,但更易于使用。这里最大的好处是您的session在整个Scenario中保持透明。关于Cucumber的另一件事是您(应该)从使用您的代码的浏览器或客户端的角度进行测试。如果您愿意,您可以使用步骤来构建对象和设置状态,但通常您
这个问题在这里已经有了答案:关闭10年前。PossibleDuplicate:Pythonconditionalassignmentoperator对于这样一个简单的问题表示歉意,但是谷歌搜索||=并不是很有帮助;)Python中是否有与Ruby和Perl中的||=语句等效的语句?例如:foo="hey"foo||="what"#assignfooifit'sundefined#fooisstill"hey"bar||="yeah"#baris"yeah"另外,类似这样的东西的通用术语是什么?条件分配是我的第一个猜测,但Wikipediapage跟我想的不太一样。
什么是ruby的rack或python的Java的wsgi?还有一个路由库。 最佳答案 来自Python标准PEP333:Bycontrast,althoughJavahasjustasmanywebapplicationframeworksavailable,Java's"servlet"APImakesitpossibleforapplicationswrittenwithanyJavawebapplicationframeworktoruninanywebserverthatsupportstheservletAPI.ht
华为OD机试题本篇题目:明明的随机数题目输入描述输出描述:示例1输入输出说明代码编写思路最近更新的博客华为od2023|什么是华为od,od薪资待遇,od机试题清单华为OD机试真题大全,用Python解华为机试题|机试宝典【华为OD机试】全流程解析+经验分享,题型分享,防作弊指南华为o
我想解析一个已经存在的.mid文件,改变它的乐器,例如从“acousticgrandpiano”到“violin”,然后将它保存回去或作为另一个.mid文件。根据我在文档中看到的内容,该乐器通过program_change或patch_change指令进行了更改,但我找不到任何在已经存在的MIDI文件中执行此操作的库.他们似乎都只支持从头开始创建的MIDI文件。 最佳答案 MIDIpackage会为您完成此操作,但具体方法取决于midi文件的原始内容。一个MIDI文件由一个或多个音轨组成,每个音轨是十六个channel中任何一个上的
本文主要介绍在使用Selenium进行自动化测试或者任务时,对于使用了iframe的页面,如何定位iframe中的元素文章目录场景描述解决方案具体代码场景描述当我们在使用Selenium进行自动化测试的时候,可能会遇到一些界面或者窗体是使用HTML的iframe标签进行承载的。对于iframe中的标签,如果直接查找是无法找到的,会抛出没有找到元素的异常。比如近在咫尺的例子就是,CSDN的登录窗体就是使用的iframe,大家可以尝试通过F12开发者模式查看到的tag_name,class_name,id或者xpath来定位中的页面元素,会抛出NoSuchElementException异常。解决
2022/8/4更新支持加入水印水印必须包含透明图像,并且水印图像大小要等于原图像的大小pythonconvert_image_to_video.py-f30-mwatermark.pngim_dirout.mkv2022/6/21更新让命令行参数更加易用新的命令行使用方法pythonconvert_image_to_video.py-f30im_dirout.mkvFFMPEG命令行转换一组JPG图像到视频时,是将这组图像视为MJPG流。我需要转换一组PNG图像到视频,FFMPEG就不认了。pyav内置了ffmpeg库,不需要系统带有ffmpeg工具因此我使用ffmpeg的python包装p
ValidPalindromeGivenastring,determineifitisapalindrome,consideringonlyalphanumericcharactersandignoringcases. [#125]Example:"Aman,aplan,acanal:Panama"isapalindrome."raceacar"isnotapalindrome.Haveyouconsiderthatthestringmightbeempty?Thisisagoodquestiontoaskduringaninterview.Forthepurposeofthisproblem
是否可以在PyYAML或Ruby的Psych引擎中禁用创建anchor和引用(并有效地显式列出冗余数据)?也许我在网上搜索时遗漏了一些东西,但在Psych中似乎没有太多可用的选项,而且我也无法确定PyYAML是否允许这样做.基本原理是我必须序列化一些数据并将其以可读的形式传递给一个不是真正的技术同事进行手动验证。有些数据是多余的,但我需要以最明确的方式列出它们以提高可读性(anchor和引用是提高效率的好概念,但不是人类可读性)。Ruby和Python是我选择的工具,但如果有其他一些相当简单的方法来“展开”YAML文档,它可能就可以了。 最佳答案