Python 程序运行了一个星期,然后莫名其妙地失败了

Python program runs for a week, then fails mysteriously

我有一个 python 程序 运行 正常,然后在很长时间后失败,我不明白为什么会这样。

这是为了在我的 raspberry pi 上驱动 PiGlow 板。

没有更好的办法,我让它以二进制格式显示时间,clock.py,由制造商提供来演示电路板。

代码如下所示:

from pyglow import PyGlow
from datetime import datetime

pyglow = PyGlow()

while True:
    time = datetime.now().time()
    hour,min,sec = str(time).split(":")
    sec,micro = str(sec).split(".")

    # do stuff with the hour, min, sec, write them to the LEDs

# that's all, no delay or anything else, so the loop runs like crazy

它通常会 运行 一天或一周,然后失败,像这样:

pi@pi ~/pyglow $ sudo python clock.py    
Traceback (most recent call last):    
  File "clock.py", line 37, in <module>  
    sec,micro = str(sec).split(".")    
ValueError: need more than 1 value to unpack    

经过一些研究(主要是在 SE 上),我的猜测是当它失败时,这是因为 str().split(".") 只返回了一个值,而程序期望返回两个值。也许如果不幸落在小数点后没有任何内容的第二个边界上?

如果重要的话,那就是Python 2.7.

我是 Python 的新手,所以我不会马上跳出来。
你能看出问题是什么吗?
您会在此程序中更改什么以防止出现这种情况?

当微秒为零时(是的,这偶尔是可能的)你在秒的字符串表示中没有点。

您可以使用 Python date/time 属性而不是解析字符串表示形式:

from datetime import datetime
time = datetime.now().time()
hour, min, sec, micro = time.hour, time.minute, time.second, time.microsecond

如果您必须使用零填充(02 而不是 2)字符串,您可以使用字符串格式:

hour, min, sec, micro = '{:02d}'.format(time.hour), '{:02d}'.format(time.minute), '{:02d}'.format(time.second), '{:06d}'.format(time.microsecond)

通过这样做来阻止这种情况发生

from datetime import datetime

while True:
    time = datetime.now().time()
    hour,min,sec = str(time).split(":")
    print sec
    if '.' in sec:
        sec,micro = str(sec).split(".")
    else:
        micro = 0
    print 'sec=%s micro=%s' % (sec, micro)

当您精确到没有微秒的一秒时,就会发生这种情况。因此,如果您检查“.”如果您没有找到它,请将 micro 设置为 0。

其中还有一些打印语句来展示它是如何工作的。

诚然,最好将时间值从头到尾都视为数字,而不要包含字符串。

是的,它正在发生,因为您在没有任何毫秒的情况下获得整秒。在更好的 CPU 上,您将在几秒钟后收到此错误。

>>> while True:
...     time = datetime.now().time()
...     hour,min,sec = str(time).split(":")
...     try:
...         sec,micro = str(sec).split(".")
...     except ValueError:
...         print str(time)
...         raise
...
23:08:23
Traceback (most recent call last):
  File "<stdin>", line 5, in <module>
ValueError: need more than 1 value to unpack

除了其他答案(Selcuk 的答案似乎更好)之外,您还可以保护您的声明有例外:

try:
    sec, micro = str(sec).split('.')
except ValueError as e:
    sec, micro = sec, '0'