代码之家  ›  专栏  ›  技术社区  ›  Elliot

在python中,多个try异常后跟一个else

  •  4
  • Elliot  · 技术社区  · 15 年前

    除了那些只有在所有子句都成功的情况下才触发一个else的子句之外,是否还有其他方法可以进行几个连续的try?

    举个例子:

     try:
        private.anodization_voltage_meter = Voltmeter(voltage_meter_address.value) #assign voltmeter location
    except(visa.VisaIOError): #channel time out
        private.logger.warning('Volt Meter is not on or not on this channel')
    try:
        private.anodization_current_meter = Voltmeter(current_meter_address.value) #assign voltmeter as current meter location
    except(visa.VisaIOError): #channel time out
        private.logger.warning('Ammeter is not on or not on this channel')
    try:
        private.sample_thermometer = Voltmeter(sample_thermometer_address.value)#assign voltmeter as thermomter location for sample.
    except(visa.VisaIOError): #channel time out
        private.logger.warning('Sample Thermometer is not on or not on this channel')
    try:
        private.heater_thermometer = Voltmeter(heater_thermometer_address.value)#assign voltmeter as thermomter location for heater.
    except(visa.VisaIOError): #channel time out
        private.logger.warning('Heater Thermometer is not on or not on this channel')
    else:
        private.logger.info('Meters initialized')
    

    如你所见,你只想打印 meters initialized 然而,如果它们全部熄灭,就如目前所写,它只取决于加热器的温度计。有什么方法可以把这些叠起来吗?

    5 回复  |  直到 9 年前
        1
  •  3
  •   strpeter davidsheldon    9 年前

    您可以保留一个布尔值,在开始时初始化为: everythingOK=True 然后将其设置为 False 在所有的异常块中,只有当为真时才记录最后一行。

        2
  •  6
  •   richo    15 年前

    就我个人而言,我只是有一个旅行变量 init_ok 或者一些。

    将其设置为true,并让所有的except子句将其设置为false,然后在末尾进行测试?

        3
  •  6
  •   Ignacio Vazquez-Abrams    15 年前

    考虑打破 try/except 结构转换为返回 True 如果通话正常 False 如果失败,则使用例如 all() 他们都成功了:

    def initfunc(structure, attrname, address, desc):
      try:
        var = Voltmeter(address.value)
        setattr(structure, attrname, var)
        return True
      except(visa.VisaIOError):
        structure.logger.warning('%s is not on or not on this channel' % (desc,))
    
    if all([initfunc(*x) for x in [(private, 'anodization_voltage_meter', voltage_meter_address, 'Volt Meter'), ...]]):
      private.logger.info('Meters initialized')
    
        4
  •  6
  •   John La Rooy    15 年前

    试试这个。保持第一次异常后不停止的原始行为

    success = True
    for meter, address, message in (
            ('anodization_voltage_meter',voltage_meter_address,'Volt Meter is not on or not on this channel'),
            ('anodization_current_meter',current_meter_address,'Ammeter is not on or not on this channel'),
            ('sample_thermometer',sample_thermometer_address,'Sample Thermometer is not on or not on this channel'),
            ('heater_thermometer',heater_thermometer_address,'Heater Thermometer is not on or not on this channel')):
       try:
           setattr(private,meter, Voltmeter(address.value):
       except (visa.VisaIOError,):
           success = False
           private.logger.warning(message)
    
    if success: # everything is ok
        private.logger.info('Meters initialized')
    
        5
  •  2
  •   user97370    15 年前

    您有许多非常相似的对象,在这种情况下,最好统一处理它们并使用数据驱动的方法。

    所以,我先从你的 ..._meter_address 物体。对我来说,它们听起来像是仪表的配置,所以我有一个类,看起来像这样:

    class MeterConfiguration(object):
        def __init__(self, name, address):
            self.name = name
            self.address = address
    
        def english_name(self):
            """A readable form of the name for this meter."""
            return ' '.join(x.title() for x in self.name.split('_')) + ' Meter'
    

    也许您还有更多的配置(当前存储在变量中)可以在这里输入。

    然后,我会有一个总结,所有米,你的程序处理。我正在静态地创建这些信息,但是从配置文件中读取这些信息的全部或部分可能是正确的。我不知道你的地址是什么样子,所以我编了些东西:)

    ALL_METERS = [
        MeterConfiguration('anodization_voltage', 'PORT0001'),
        MeterConfiguration('anodization_current', 'PORT0002'),
        MeterConfiguration('sample_thermometer', 'PORT0003'),
        MeterConfiguration('heater_thermometer', 'PORT0004')
    ]
    

    很酷,现在所有的配置都在一个地方,我们可以用它来让事情变得统一和简单。

    private.meters = {}
    any_errors = False
    for meter in ALL_METERS:
        try:
            private.meters[meter.name] = Voltmeter(meter.address)
        except VisaError:
            logging.error('%s not found at %s', meter.english_name(), meter.address)
            any_errors = True
    if not any_errors:
        logging.info('All meters initialized.')
    

    例如,您可以使用 private.meters['anodization_voltage'] 引用一个特定的表,或者在需要对所有表都做些什么的情况下对这些表进行迭代。