<p>对于所有这些<code>try:...except</code>块,您现有的代码有点奇怪,而且很危险。这很危险,因为它忽略了所有应该<strong>而不是</strong>的错误。例如:试图使用未定义变量的值、被零除错误和完全语法错误。在</p>
<hr/>
<p>你可以用类做你想做的事情,但是对于这样的事情,我更倾向于使用一个简单的<code>dict</code>。我将发布这两种方法的代码,以帮助您做出决定(或增加您的困惑:)。在</p>
<p>显然,我没有你的监控硬件连接到我的串行端口,所以为了测试这段代码,我写了一个简单的生成器函数,它创建了随机的假数据。希望您可以很容易地修改我的代码。在</p>
<p>首先,使用一个类的代码,该类保存当前的总数和读取数;这个类还有一个属性,可以按需计算平均值。所以如果你愿意,你可以做<code>print dust.total, flow.mean</code>之类的事情。在</p>
<pre><code>from random import seed, random
#A generator to make simulated data
def fake_data(n):
for i in range(n):
d = 0.005 + 0.005 * random()
f = 1.5 + random()
t = 20.0 + 5.0 * random()
h = int(40 + 10.0 * random())
p = 1005.0 + 10.0 * random()
s = '%07.3f,%3.1f,%-4.1f,%03d,%6.1f' % (d, f, t, h, p)
yield [s]
class Data(object):
def __init__(self, name):
self.name = name
self.total = 0
self.numberOfReads = 0
def __repr__(self):
fmt = "Data(name='%s', total=%f, number=%d, mean=%f)"
return fmt % (self.name, self.total, self.numberOfReads, self.mean)
def __str__(self):
fmt = '%s\nmean: %f\nnumber: %d\ntotal: %f\n'
return fmt % (self.name, self.mean, self.numberOfReads, self.total)
def add(self, value):
self.total += value
self.numberOfReads += 1
@property
def mean(self):
try:
return float(self.total) / float(self.numberOfReads)
except ZeroDivisionError:
return None
#Seed the randomiser
seed(1)
#Initialise the Data instances
dust = Data('Dust')
flow = Data('Flow')
temp = Data('Temperature')
rh = Data('Relative Humidity')
press = Data('Pressure')
for readData in fake_data(10):
## Split comma delimited data into dust, flow, temperature, relative humidity, pressure
## for example data comes in as 000.007,2.0,+21.7,046,1010.0
print readData
measData = readData[0].split(',')
#Convert data strings to floats
dustR, flowR, tempR, rhR, pressR = [float(s) for s in measData]
#Add new data to current totals
dust.add(dustR)
flow.add(flowR)
temp.add(tempR)
rh.add(rhR)
press.add(pressR)
print
for a in (dust, flow, temp, rh, press):
print a
</code></pre>
<p><strong>输出</strong></p>
^{pr2}$
<hr/>
<p>下面是使用<code>dict</code>的版本。我已经将随机化器种子设置为相同的值,这样假数据与前一个版本相同。在</p>
<pre><code>from random import seed, random
#A generator to make simulated data
def fake_data(n):
for i in range(n):
d = 0.005 + 0.005 * random()
f = 1.5 + random()
t = 20.0 + 5.0 * random()
h = int(40 + 10.0 * random())
p = 1005.0 + 10.0 * random()
s = '%07.3f,%3.1f,%-4.1f,%03d,%6.1f' % (d, f, t, h, p)
yield [s]
#Seed the randomiser
seed(1)
#data field names
fields = ('Dust', 'Flow', 'Temp', 'rh', 'press')
#initialise the data dictionary
data = dict.fromkeys(fields, 0.0)
nReading = 0
for readData in fake_data(10):
nReading += 1
## Split comma delimited data into dust, flow, temperature, relative humidity, pressure
## for example data comes in as 000.007,2.0,+21.7,046,1010.0
print nReading, readData
measData = readData[0].split(',')
#Convert data strings to floats
floatData = [float(s) for s in measData]
#Add new data to current totals
for key, value in zip(fields, floatData):
data[key] += value
print '\nNumber of readings = %d\n' % nReading
nReading = float(nReading)
for key in fields:
total = data[key]
mean = total / nReading
print '%s\nmean: %f\ntotal: %f\n' % (key, mean, total)
</code></pre>
<p><strong>输出</strong></p>
<pre><code>1 ['000.006,2.3,23.8,042,1010.0']
2 ['000.007,2.2,23.9,040,1005.3']
3 ['000.009,1.9,23.8,040,1009.5']
4 ['000.009,1.7,24.7,049,1005.3']
5 ['000.005,2.0,24.7,043,1007.2']
6 ['000.007,1.5,21.1,044,1010.0']
7 ['000.006,1.7,21.1,044,1007.9']
8 ['000.005,2.3,22.8,046,1006.9']
9 ['000.010,2.4,20.6,043,1012.2']
10 ['000.009,2.4,22.1,048,1011.7']
Number of readings = 10
Dust
mean: 0.007300
total: 0.073000
Flow
mean: 2.040000
total: 20.400000
Temp
mean: 22.860000
total: 228.600000
rh
mean: 43.900000
total: 439.000000
press
mean: 1008.600000
total: 10086.000000
</code></pre>
<hr/>
<p>下面是一个使用<code>try:... except</code>验证输入数据的简单示例。在</p>
<pre><code>data = [
'1.1 2.2 3.3',
'4 5',
'6 garbage bytes',
'7 8 9 10',
'11 12 13',
]
for i, line in enumerate(data):
print '\nLine %d: %r' % (i, line)
row = line.split()
if len(row) != 3:
print 'Bad row length. Should be 3 not', len(row)
continue
try:
a, b, c = [float(s) for s in row]
except ValueError as err:
print 'Conversion error:', err
continue
print 'Data %d: a=%f, b=%f, c=%f' % (i, a, b, c)
</code></pre>
<p><strong>输出</strong></p>
<pre><code>Line 0: '1.1 2.2 3.3'
Data 0: a=1.100000, b=2.200000, c=3.300000
Line 1: '4 5'
Bad row length. Should be 3 not 2
Line 2: '6 garbage bytes'
Conversion error: invalid literal for float(): garbage
Line 3: '7 8 9 10'
Bad row length. Should be 3 not 4
Line 4: '11 12 13'
Data 4: a=11.000000, b=12.000000, c=13.000000
</code></pre>