我在写一个用于读取覆盆子pi上的温度传感器(DS18B20)的脚本时遇到了麻烦。 我有一个工作脚本,但有时传感器掉了,然后脚本也停止了。 我试图通过集成try-except语句来制作更强大的版本。目标是如果其中一个传感器没有反应,则继续进行该范围内的下一个传感器。如果我通过插入其中一个传感器来模拟传感器故障,脚本将停止对所有传感器(而不是已插入的传感器)进行测量。它并没有给我一个错误。有任何想法吗?
这是带有try语句的脚本的一部分:
if time.time() <= timeout:
for index in range (numsensors):
try:
def read_temp_raw(): # gets the temps one by one
f = open(device_file[index], 'r')
lines = f.readlines()
f.close()
return lines
def read_temp(): # checks the received temperature for errors
lines = read_temp_raw()
while lines[0].strip()[-3:] != 'YES':
time.sleep(0.2)
lines = read_temp_raw()
equals_pos = lines[1].find('t=')
if equals_pos != -1:
temp_string = lines[1][equals_pos+2:]
# set proper decimal place for deg C
temp = float(temp_string) / 1000.0
# Round temp to x decimal points --> round(temp,x)
temp = round(temp, 2)
return temp
reading = (read_temp())
temp[index].append(reading)
print device[index],"=", temp[index]
continue
except IOError:
print "Error"
答案 0 :(得分:0)
使用try-except
构造使基础系统更多
强健?
为什么是指示传感器失败时没有出现任何错误的代码?
<强> A1:强>
try-except
条款听起来不言自明。救生包,但事实并非如此。
必须完全理解 各种 exceptions
- 类型代码期望面对面和如何处理它们中的每一个。天真或错误地使用这种语法构造有效地掩盖了调试雷达屏幕中的其余异常,使得未处理的案例在黑暗的沉默中失败,超出您的控制而根本不了解它们。真正的“健壮性”和“失败恢复力”不是这个。
此代码示例将保留隐藏的所有真实冲突,除了列出的唯一冲突IOError
,但如果不会发生,则所有其他冲突都会被处理:
if time.time() <= timeout: # START if .time() is still before a T/O
for index in range (numsensors): # ITERATE over all sensors
try: # TRY:
<<<something>>> # <<<something>>>
except IOError: # EXC IOError:
<<<IOError__>>> # Handle EXC.IOError
猜测所有def...(..):
- s可能属于代码的非重复部分,在if:/for:
之前,因为您不需要“即时”修改代码,是吗? ?
def read_temp_raw(): # DEF: gets the temps one by one
f = open(device_file[index],'r') # SET aFileHANDLE access to IO.DEV ( beware var index "visibility" )
lines = f.readlines() # IO.DEV.READ till <EoF>
f.close() # IO.DEV.CLOSE
return lines # RET all lines
def read_temp(): # DEF: checks the received temperature for errors
lines = read_temp_raw() # GET lines from read_temp_raw()
while lines[0].strip()[-3:]!='YES': # WHILE last-3Bytes of 1st-line!="YES"
time.sleep(0.2) # NOP/Sleep()
lines = read_temp_raw() # GET lines again (beware var index)
equals_pos =lines[1].find('t=') # SET position of 't=' in 2nd-line
if equals_pos != -1: # IF position != -1
temp_string = lines[1][equals_pos+2:]
temp = float(temp_string) \
/ 1000.0 # DIV( 1000) decimal place for deg C
temp = round(temp, 2) # ROUND temp to x decimal points --> round(temp,x)
return temp # RET->
# ----------------------------- # ELSE: re-loop in WHILE
# -------------------------------- # LOOP AGAIN AD INFIMUM
A2:发布的代码中的try-except
子句期望只处理一种异常 - IOError
- 仅当实际的IO.DEV操作因I / O相关原因而失败时才会实例化,这并不意味着您实际上“取消插入”传感器,而IO .DEV仍然存在并且可以携带它的IO.DEV.READ(s),因此exceptions.EnvironmentError.IOError
不是raise
- d
这意味着,IO.DEV.READ(s)发生并且代码根据条件WHILE last-3Bytes of 1st-line
在无限循环中指示,因为第一行“仍然”不会以“是”。
Q.E.D。
回到这个问题,您可能更愿意为真实案例设置一个更安全的测试,在传感器网络扫描期间可能会出现错误的输入。
原则可能如下:
f.close() # IO.DEV.CLOSE
if ( len(lines) < 2 ): # IF <<lines>> are nonsense:
return [ "NULL_LENGTH_READING still with CODE EXPECTED ACK-SIG-> YES", \
"SIG ERROR FOR POST-PROCESSOR WITH AN UNREALISTIC VALUE t=-99999999" \
]
return( lines ) # OTHERWISE RET( lines )