Python 异常处理

#   Python - 异常处理
#  异常和错误的概念
#                 错误:
#                     语法错误:比如写成:  dle xxx()
#                     逻辑错误: if age < 18 : print("已经成年")
#                 异常:多出现在程序的执行过程中,出现的未知错误;语法和逻辑都正确
#                       异常可以通过代码来修复
# 常见的系统异常
#                   除0异常;
#                           异常名称:ZeroDivisionError
#                   名字异常:用了一个没有定义的名称;
#                           如:print(name);
#                           异常名称:NameError
#                   类型异常:"a" + 10
#                           异常名称:TypeError
#                   索引异常:l = [1,2]  l[2]
#                           异常名称:IndexError
#                   键值异常:key = {"name":"abc", "age" : 18}   key = {"name":"abc", "age" : 18}
#                           异常名称:KeyError
#                   值异常:int("abc")
#                           异常名称:ValueError
#                   属性异常:name = "abc" print(name.xxx)
#                           异常名称:AttributeError
#                   迭代器异常:
#                         it = iter([1, 2])
#                         next(it)
#                         next(it)
#                         next(it)
#                             异常名称:StopIteration



#   情况一
try:
    1 / 0
    print(name)
except (ZeroDivisionError, NameError) as e:
    print(e)
else:
    print("else")
finally:
    print("finally")

#   情况二, 下面为优,Exception
try:
    # 1 / 0
    print(name)
except Exception as e:
    print(e)
else:
    print("else")
finally:
    print("finally")


#   ----------------    上下文管理器  ---------------------
#   可以自定义上下文管理器:在执行一个主题时先定义 __enter__, __exit__
class Test():
    def __enter__(self):
        print("enter")
        return 1;

    def __exit__(self, exc_type, exc_val, exc_tb):
        print(self, exc_type, exc_val, exc_tb)
        #得到异常的错误信息,可以把这些形象写入到日子文件里
        import traceback
        traceback.extract_tb(exc_tb)

        print("exit")
        return True #   返回True,异常错误信息不会往外传,否则会往外传


print(Test().__enter__())   # 1
#   with 语句
#   as x 其中x代表前面表达式中__enter__的返回值
with Test() as t:
    print("body", t)
    1 / 0

#   输出如下信息:
    # enter
    # body  None
    # <__main__.Test object at 0x01CBB9D0> None None None
    #   1 / 0 显示为下面的结果
    #<__main__.Test object at 0x0343B9D0> <class 'ZeroDivisionError'> division by zero <traceback object at 0x03525F08>
    # exit

#   yield 前面的成为 __enter__
#   yield 后面的"return" 成为 __enter__的返回值
#   yield 后面下面的语句成为__exit__的内容
def test():
    print(1)
    yield "return"
    print(2)

#   通过contextlib 来构造上下文管理器
import contextlib
@contextlib.contextmanager
def ze():
    try:
        yield
    except Exception as e:
        print(e)

#   division by zero
with ze():
    10 / 0

#  快速把对象里面有close的方法变成上下文管理器,前提是对象里面必须要有close

class Test():
    def start(self):
        print("start")

    def close(self):
        print("close")

import contextlib
with contextlib.closing(Test()) as obj:
    obj.start()

#   start
#   close

#   Python 3.0 以后的嵌套方法
#   第一种写法
with open("1.png", "rb") as from_file:
    with open("3.png", "wb") as to_file:
        content = from_file.read()
        to_file.write( content )

#   第二种写法
with open("1.png", "rb") as from_file, open("4.png", "wb") as to_file:
    content = from_file.read()
    to_file.write(content)

#   --------------------    手动抛出异常  --------------------
def set_age(age):
    if 0 <= age < 200 :
        print("你的年龄:", age)
    else:
        # print("值错误")
        #   下面的是直接抛出异常错误给外面
        raise ValueError("值错误")

set_age(18) #   你的年龄: 18
try:
    set_age(-18)
except ValueError as e:
    print(e)    #   值错误

#   ------------------- 自定义异常   -------------------------
class LessZero(Exception):
    def __init__(self, msg, error_code):
        self.msg = msg
        self.error_code = error_code

    def __str__(self):
        return self.msg + str(self.error_code)

def set_age(age):
    if 0 <= age < 200 :
        print("你的年龄:", age)
    else:
        # print("值错误")
        #   下面的是直接抛出异常错误给外面
        raise LessZero("值错误", 404)

try:
    set_age(-18)
except LessZero as e:
    print(e)    #   值错误404

 

posted @ 2018-03-23 09:52  delphiclub  阅读(134)  评论(0编辑  收藏  举报