Python 合并';而不是';用try/除了

Python 合并';而不是';用try/除了,python,python-2.7,while-loop,try-catch,Python,Python 2.7,While Loop,Try Catch,我得到一个带有urllib2的页面,然后用lxml解析它。通常有两种情况会出错:一种是urllib2.urleror,另一种是httplib.incompleread def get_page(url): response = None while not response: try: response = urllib2.urlopen(url) except urllib2.URLError: r

我得到一个带有
urllib2
的页面,然后用
lxml
解析它。通常有两种情况会出错:一种是
urllib2.urleror
,另一种是
httplib.incompleread

def get_page(url):
    response = None
    while not response:
        try:
            response = urllib2.urlopen(url)
        except urllib2.URLError:
            response = urllib2.urlopen(url)
        except httplib.IncompleteRead:
            print '**** IncompleteRead for response from %s, retrying' % url
        html_parser = etree.HTMLParser()
        tree = etree.parse(response, html_parser)
        return tree

这里有几个明显的问题:

  • 除之外的第一个
    执行与前一个
    try
    完全相同的操作
  • 无论是否有
    响应
    ,都将尝试使用
    lxml进行解析
  • 因此:

  • 除了,在第一个
    中需要加入什么?
    pass
    可接受吗
  • 我的理解是,在
    try
    中只能尝试一个操作,因此我不愿意将解析移到下面。实际上,一个函数本身应该只执行一个动作——解析是否属于它自己的函数

  • 您可以通过组合使用
    continue
    break
    语句来处理这些情况
    continue
    将跳回while循环的顶部,
    break
    将跳出while循环

    def get_page(url):
        response = None
        while not response:
            try:
                response = urllib2.urlopen(url)
            except urllib2.URLError:
                continue  # No response, try again
            except httplib.IncompleteRead:
                print '**** IncompleteRead for response from %s, retrying' % url
                break  # Bad response, don't try again?
            html_parser = etree.HTMLParser()
            tree = etree.parse(response, html_parser)
            return tree
    

    您也可以在这里混合使用其他流控制工具(如
    else
    子句,用于
    try
    ,它仅在块中未发生异常时执行):

    与之相反:

    try:
        raise Exception
    except Exception as err:
        print("You will see this.")
    else:
        print("Don't see this.")
    

    您可以通过组合使用
    continue
    break
    语句来处理这些情况
    continue
    将跳回while循环的顶部,
    break
    将跳出while循环

    def get_page(url):
        response = None
        while not response:
            try:
                response = urllib2.urlopen(url)
            except urllib2.URLError:
                continue  # No response, try again
            except httplib.IncompleteRead:
                print '**** IncompleteRead for response from %s, retrying' % url
                break  # Bad response, don't try again?
            html_parser = etree.HTMLParser()
            tree = etree.parse(response, html_parser)
            return tree
    

    您也可以在这里混合使用其他流控制工具(如
    else
    子句,用于
    try
    ,它仅在块中未发生异常时执行):

    与之相反:

    try:
        raise Exception
    except Exception as err:
        print("You will see this.")
    else:
        print("Don't see this.")
    

    我认为您希望将解析移出
    while
    循环,而不是进入
    try
    块。这样,您就可以继续循环尝试获取有效响应,并且只有在请求成功时才尝试解析

    def get_page(url):
        response = None
        while not response:
            try:
                response = urllib2.urlopen(url)
            except urllib2.URLError:
                print '**** URLError for response from %s, retrying' % url
            except httplib.IncompleteRead:
                print '**** IncompleteRead for response from %s, retrying' % url
    
        html_parser = etree.HTMLParser()
        tree = etree.parse(response, html_parser)
        return tree
    
    我还更新了
    URLError
    除外
    块,使其工作原理与
    不完整
    块基本相同。实际上,我不确定这是否合适,因为重试可能无法修复某些
    URLError
    s(例如,如果服务器不存在,则重试时可能不会更改)。如果它应该是一个致命错误(至少对该函数是致命的),您可能希望在该
    块中
    提升
    ,而不是让循环继续。这里有一个版本比
    incompleread
    s更严重地处理
    URLErrors

    def get_page(url):
        response = None
        while not response:
            try:
                response = urllib2.urlopen(url)
            except urllib2.URLError:
                print '**** URLError for response from %s, giving up' % url
                raise
            except httplib.IncompleteRead:
                print '**** IncompleteRead for response from %s, retrying' % url
    
        html_parser = etree.HTMLParser()
        tree = etree.parse(response, html_parser)
        return tree
    

    raise
    关键字本身(后面没有表达式)重新引发当前异常。如果这在应用程序中更有意义,您还可以引发不同的错误(例如,
    ValueError
    ,表示提供的URL不好)。

    我认为您希望将解析移出
    while
    循环,而不是进入
    try
    块。这样,您就可以继续循环尝试获取有效响应,并且只有在请求成功时才尝试解析

    def get_page(url):
        response = None
        while not response:
            try:
                response = urllib2.urlopen(url)
            except urllib2.URLError:
                print '**** URLError for response from %s, retrying' % url
            except httplib.IncompleteRead:
                print '**** IncompleteRead for response from %s, retrying' % url
    
        html_parser = etree.HTMLParser()
        tree = etree.parse(response, html_parser)
        return tree
    
    我还更新了
    URLError
    除外
    块,使其工作原理与
    不完整
    块基本相同。实际上,我不确定这是否合适,因为重试可能无法修复某些
    URLError
    s(例如,如果服务器不存在,则重试时可能不会更改)。如果它应该是一个致命错误(至少对该函数是致命的),您可能希望在该
    块中
    提升
    ,而不是让循环继续。这里有一个版本比
    incompleread
    s更严重地处理
    URLErrors

    def get_page(url):
        response = None
        while not response:
            try:
                response = urllib2.urlopen(url)
            except urllib2.URLError:
                print '**** URLError for response from %s, giving up' % url
                raise
            except httplib.IncompleteRead:
                print '**** IncompleteRead for response from %s, retrying' % url
    
        html_parser = etree.HTMLParser()
        tree = etree.parse(response, html_parser)
        return tree
    

    raise
    关键字本身(后面没有表达式)重新引发当前异常。如果这在应用程序中更有意义,您还可以引发不同的错误(例如,
    ValueError
    ,表示提供的URL不好)。

    如果您想在这两种情况下都重试,您可以执行
    除了(urllib2.urleror,httplib.IncompleteRead):
    以使用相同的代码处理两个异常。“这里有几个明显的问题”--这些问题对我们来说并不明显,因为您没有实际描述代码应该做什么。例如,如果引发
    URLError
    会发生什么?如果引发
    UncompleteRead
    会发生什么?如果您想在这两种情况下重试,您可以执行
    ,除了(urllib2.urleror,httplib.IncompleteRead):
    用相同的代码处理两个异常。”这里有几个明显的问题“--这些问题对我们来说并不明显,因为您没有实际描述代码应该做什么。例如,如果引发
    URLError
    会发生什么?如果引发
    UncompleteRead
    会发生什么?