Python中级教程 第三课:面向对象编程深入与装饰器

浏览量:78 次 发布时间:2026-01-15 18:11 作者:明扬工控商城 下载docx

最近更新:Python中级教程 第三课:面向对象编程深入与装饰器

第一部分:面向对象编程高级概念

1. 类方法和静态方法

python

class Student:

   school = "清华大学"  # 类属性

   

   def __init__(self, name, age):

       self.name = name  # 实例属性

       self.age = age

   

   # 实例方法 - 操作实例属性

   def display_info(self):

       return f"{self.name}, {self.age}岁, 来自{self.school}"

   

   # 类方法 - 操作类属性

   @classmethod

   def change_school(cls, new_school):

       cls.school = new_school

       return f"学校已更改为:{new_school}"

   

   # 静态方法 - 不依赖实例或类

   @staticmethod

   def is_adult(age):

       return age >= 18

   

   @staticmethod

   def calculate_grade(score):

       if score >= 90:

           return "A"

       elif score >= 80:

           return "B"

       else:

           return "C"


# 使用示例

s1 = Student("张三", 20)

print(s1.display_info())  # 实例方法

print(Student.change_school("北京大学"))  # 类方法

print(s1.is_adult(25))  # 静态方法

print(Student.calculate_grade(85))  # 静态方法

2. 属性装饰器 (@property)

python

class Circle:

   def __init__(self, radius):

       self._radius = radius  # 使用_表示受保护的属性

   

   @property

   def radius(self):

       """获取半径"""

       return self._radius

   

   @radius.setter

   def radius(self, value):

       """设置半径,必须为正数"""

       if value <= 0:

           raise ValueError("半径必须为正数")

       self._radius = value

   

   @property

   def diameter(self):

       """直径是只读属性"""

       return self._radius * 2

   

   @property

   def area(self):

       """面积是计算属性"""

       import math

       return math.pi * self._radius ** 2

   

   @property

   def circumference(self):

       """周长是计算属性"""

       import math

       return 2 * math.pi * self._radius


# 使用示例

c = Circle(5)

print(f"半径: {c.radius}")

print(f"直径: {c.diameter}")

print(f"面积: {c.area:.2f}")

print(f"周长: {c.circumference:.2f}")


# 修改半径

c.radius = 10

print(f"修改后面积: {c.area:.2f}")


# 尝试设置非法值

try:

   c.radius = -5

except ValueError as e:

   print(f"错误: {e}")

3. 类的继承与多态深入

python

# 基类

class Animal:

   def __init__(self, name, age):

       self.name = name

       self.age = age

   

   def speak(self):

       raise NotImplementedError("子类必须实现此方法")

   

   def move(self):

       return f"{self.name}正在移动"

   

   def __str__(self):

       return f"{self.__class__.__name__}: {self.name}, {self.age}岁"


# 子类1

class Dog(Animal):

   def __init__(self, name, age, breed):

       super().__init__(name, age)  # 调用父类初始化

       self.breed = breed

   

   def speak(self):

       return "汪汪!"

   

   def fetch(self):

       return f"{self.name}正在捡球"

   

   def __str__(self):

       base_str = super().__str__()

       return f"{base_str}, 品种: {self.breed}"


# 子类2

class Cat(Animal):

   def __init__(self, name, age, color):

       super().__init__(name, age)

       self.color = color

   

   def speak(self):

       return "喵喵!"

   

   def climb(self):

       return f"{self.name}正在爬树"

   

   def move(self):  # 重写父类方法

       return f"{self.name}悄悄地走动"


# 子类3 - 多重继承示例

class Bird:

   def __init__(self, wingspan):

       self.wingspan = wingspan

   

   def fly(self):

       return "正在飞翔"


class Parrot(Animal, Bird):  # 多重继承

   def __init__(self, name, age, wingspan, vocabulary):

       Animal.__init__(self, name, age)  # 显式调用父类初始化

       Bird.__init__(self, wingspan)  # 显式调用父类初始化

       self.vocabulary = vocabulary

   

   def speak(self):

       if self.vocabulary:

           return f"鹦鹉说: {self.vocabulary[0]}"

       return "叽叽喳喳"

   

   def learn_word(self, word):

       self.vocabulary.append(word)

       return f"{self.name}学会了新词: {word}"


# 使用示例

animals = [

   Dog("旺财", 3, "金毛"),

   Cat("咪咪", 2, "白色"),

   Parrot("小绿", 1, 30, ["你好", "再见"])

]


for animal in animals:

   print(animal)  # 调用__str__方法

   print(f"叫声: {animal.speak()}")  # 多态

   print(f"移动: {animal.move()}")

   

   # 检查特定方法

   if isinstance(animal, Dog):

       print(animal.fetch())

   elif isinstance(animal, Cat):

       print(animal.climb())

   elif isinstance(animal, Parrot):

       print(animal.fly())

       print(animal.learn_word("谢谢"))

   

   print("-" * 30)

4. 抽象基类 (ABC)

python

from abc import ABC, abstractmethod

import math


# 抽象基类

class Shape(ABC):

   def __init__(self, name):

       self.name = name

   

   @abstractmethod

   def area(self):

       """计算面积"""

       pass

   

   @abstractmethod

   def perimeter(self):

       """计算周长"""

       pass

   

   def display_info(self):

       return f"{self.name}: 面积={self.area():.2f}, 周长={self.perimeter():.2f}"


# 具体实现类

class Rectangle(Shape):

   def __init__(self, width, height):

       super().__init__("矩形")

       self.width = width

       self.height = height

   

   def area(self):

       return self.width * self.height

   

   def perimeter(self):

       return 2 * (self.width + self.height)


class Circle(Shape):

   def __init__(self, radius):

       super().__init__("圆形")

       self.radius = radius

   

   def area(self):

       return math.pi * self.radius ** 2

   

   def perimeter(self):

       return 2 * math.pi * self.radius


class Triangle(Shape):

   def __init__(self, a, b, c):

       super().__init__("三角形")

       self.a = a

       self.b = b

       self.c = c

   

   def area(self):

       # 使用海伦公式

       s = (self.a + self.b + self.c) / 2

       return math.sqrt(s * (s - self.a) * (s - self.b) * (s - self.c))

   

   def perimeter(self):

       return self.a + self.b + self.c


# 使用示例

shapes = [

   Rectangle(5, 10),

   Circle(7),

   Triangle(3, 4, 5)

]


for shape in shapes:

   print(shape.display_info())

第二部分:装饰器详解

1. 函数装饰器基础

python

# 1. 简单装饰器

def simple_decorator(func):

   def wrapper():

       print("函数执行前...")

       result = func()

       print("函数执行后...")

       return result

   return wrapper


@simple_decorator

def say_hello():

   print("Hello, World!")


say_hello()


print("\n" + "="*50 + "\n")


# 2. 带参数的装饰器

def repeat(n):

   """重复执行函数n次"""

   def decorator(func):

       def wrapper(*args, **kwargs):

           for i in range(n):

               print(f"第{i+1}次执行:")

               result = func(*args, **kwargs)

               print()

           return result

       return wrapper

   return decorator


@repeat(3)

def greet(name):

   print(f"你好, {name}!")


greet("张三")


print("\n" + "="*50 + "\n")


# 3. 保留函数元信息

from functools import wraps


def debug_decorator(func):

   @wraps(func)  # 保留原函数的元信息

   def wrapper(*args, **kwargs):

       print(f"调用函数: {func.__name__}")

       print(f"参数: args={args}, kwargs={kwargs}")

       result = func(*args, **kwargs)

       print(f"返回值: {result}")

       return result

   return wrapper


@debug_decorator

def add(a, b):

   """两个数相加"""

   return a + b


print(add(5, 3))

print(f"函数名: {add.__name__}")

print(f"函数文档: {add.__doc__}")

2. 类装饰器

python

# 1. 类作为装饰器

class Timer:

   """计时装饰器"""

   def __init__(self, func):

       self.func = func

   

   def __call__(self, *args, **kwargs):

       import time

       start_time = time.time()

       result = self.func(*args, **kwargs)

       end_time = time.time()

       print(f"函数 {self.func.__name__} 执行时间: {end_time - start_time:.6f}秒")

       return result


@Timer

def slow_function():

   import time

   time.sleep(1)

   return "执行完成"


print(slow_function())


print("\n" + "="*50 + "\n")


# 2. 带参数的类装饰器

class Retry:

   """重试装饰器"""

   def __init__(self, max_retries=3):

       self.max_retries = max_retries

   

   def __call__(self, func):

       def wrapper(*args, **kwargs):

           for attempt in range(self.max_retries):

               try:

                   result = func(*args, **kwargs)

                   print(f"第{attempt+1}次尝试成功!")

                   return result

               except Exception as e:

                   print(f"第{attempt+1}次尝试失败: {e}")

                   if attempt == self.max_retries - 1:

                       raise

           return None

       return wrapper


@Retry(max_retries=3)

def unreliable_function():

   import random

   if random.random() < 0.7:  # 70%的概率失败

       raise ValueError("随机失败!")

   return "成功!"


try:

   print(unreliable_function())

except Exception as e:

   print(f"最终失败: {e}")


print("\n" + "="*50 + "\n")


# 3. 类方法装饰器

class Cache:

   """缓存装饰器"""

   def __init__(self):

       self.cache = {}

   

   def __call__(self, func):

       def wrapper(*args, **kwargs):

           # 创建缓存键

           key = (func.__name__, args, frozenset(kwargs.items()))

           

           if key in self.cache:

               print(f"从缓存中获取结果: {key[0]}")

               return self.cache[key]

           

           result = func(*args, **kwargs)

           self.cache[key] = result

           print(f"计算结果并缓存: {key[0]}")

           return result

       return wrapper


cache = Cache()


@cache

def fibonacci(n):

   """计算斐波那契数列"""

   if n <= 1:

       return n

   return fibonacci(n-1) + fibonacci(n-2)


print(f"fibonacci(10) = {fibonacci(10)}")

print(f"再次调用 fibonacci(10) = {fibonacci(10)}")

3. 装饰器的实际应用

python

import time

from functools import wraps

from datetime import datetime


# 1. 权限验证装饰器

def require_login(func):

   @wraps(func)

   def wrapper(user, *args, **kwargs):

       if not user.get('is_authenticated', False):

           return "错误: 请先登录!"

       return func(user, *args, **kwargs)

   return wrapper


def require_admin(func):

   @wraps(func)

   def wrapper(user, *args, **kwargs):

       if not user.get('is_admin', False):

           return "错误: 需要管理员权限!"

       return func(user, *args, **kwargs)

   return wrapper


class User:

   def __init__(self, name, is_authenticated=False, is_admin=False):

       self.name = name

       self.is_authenticated = is_authenticated

       self.is_admin = is_admin


@require_login

def view_profile(user):

   return f"欢迎查看个人资料, {user.name}!"


@require_admin

def delete_user(user, target_user):

   return f"{user.name} 删除了用户 {target_user}"


# 测试

user1 = User("张三", is_authenticated=True, is_admin=False)

user2 = User("李四", is_authenticated=True, is_admin=True)


print(view_profile(user1))

print(view_profile(User("游客")))

print(delete_user(user2, "王五"))

print(delete_user(user1, "王五"))


print("\n" + "="*50 + "\n")


# 2. 日志装饰器

def log_execution(func):

   @wraps(func)

   def wrapper(*args, **kwargs):

       start_time = time.time()

       timestamp = datetime.now().strftime("%Y-%m-%d %H:%M:%S")

       

       print(f"[{timestamp}] 开始执行: {func.__name__}")

       print(f"    参数: {args}, {kwargs}")

       

       try:

           result = func(*args, **kwargs)

           end_time = time.time()

           duration = end_time - start_time

           

           print(f"[{datetime.now().strftime('%Y-%m-%d %H:%M:%S')}] 执行完成: {func.__name__}")

           print(f"    耗时: {duration:.4f}秒")

           print(f"    结果: {result}")

           

           return result

       except Exception as e:

           end_time = time.time()

           duration = end_time - start_time

           

           print(f"[{datetime.now().strftime('%Y-%m-%d %H:%M:%S')}] 执行失败: {func.__name__}")

           print(f"    耗时: {duration:.4f}秒")

           print(f"    错误: {e}")

           raise

   

   return wrapper


@log_execution

def process_data(data, multiplier=1):

   """处理数据"""

   if not data:

       raise ValueError("数据不能为空")

   

   time.sleep(0.5)  # 模拟耗时操作

   return [x * multiplier for x in data]


# 测试

print(process_data([1, 2, 3, 4, 5], multiplier=2))

print("\n")

try:

   process_data([], multiplier=2)

except ValueError:

   pass


print("\n" + "="*50 + "\n")


# 3. 性能监控装饰器

class PerformanceMonitor:

   def __init__(self):

       self.stats = {}

   

   def monitor(self, func):

       @wraps(func)

       def wrapper(*args, **kwargs):

           start_time = time.time()

           start_memory = self._get_memory_usage()

           

           result = func(*args, **kwargs)

           

           end_time = time.time()

           end_memory = self._get_memory_usage()

           

           # 更新统计信息

           if func.__name__ not in self.stats:

               self.stats[func.__name__] = {

                   'count': 0,

                   'total_time': 0,

                   'total_memory': 0

               }

           

           self.stats[func.__name__]['count'] += 1

           self.stats[func.__name__]['total_time'] += (end_time - start_time)

           self.stats[func.__name__]['total_memory'] += (end_memory - start_memory)

           

           return result

       

       return wrapper

   

   def _get_memory_usage(self):

       """获取内存使用情况"""

       import psutil

       import os

       process = psutil.Process(os.getpid())

       return process.memory_info().rss / 1024 / 1024  # 转换为MB

   

   def show_stats(self):

       """显示统计信息"""

       print("性能统计:")

       print("-" * 50)

       for func_name, stat in self.stats.items():

           avg_time = stat['total_time'] / stat['count']

           avg_memory = stat['total_memory'] / stat['count']

           print(f"{func_name}:")

           print(f"  调用次数: {stat['count']}")

           print(f"  平均时间: {avg_time:.6f}秒")

           print(f"  平均内存: {avg_memory:.2f}MB")

       print("-" * 50)


# 使用性能监控

monitor = PerformanceMonitor()


@monitor.monitor

def heavy_computation(n):

   """执行重计算"""

   result = 0

   for i in range(n):

       result += i ** 2

   return result


@monitor.monitor

def create_large_list(n):

   """创建大列表"""

   return [i for i in range(n)]


# 执行测试

for _ in range(5):

   heavy_computation(10000)


for _ in range(3):

   create_large_list(10000)


# 显示统计信息

monitor.show_stats()

4. 装饰器堆叠与参数传递

python

def decorator1(func):

   @wraps(func)

   def wrapper(*args, **kwargs):

       print("装饰器1: 执行前")

       result = func(*args, **kwargs)

       print("装饰器1: 执行后")

       return result

   return wrapper


def decorator2(func):

   @wraps(func)

   def wrapper(*args, **kwargs):

       print("装饰器2: 执行前")

       result = func(*args, **kwargs)

       print("装饰器2: 执行后")

       return result

   return wrapper


def decorator_with_args(message):

   def decorator(func):

       @wraps(func)

       def wrapper(*args, **kwargs):

           print(f"消息: {message}")

           print(f"函数: {func.__name__}")

           return func(*args, **kwargs)

       return wrapper

   return decorator


# 堆叠装饰器(从上到下应用,从下到上执行)

@decorator1

@decorator2

@decorator_with_args("这是测试函数")

def example_function(x, y):

   return f"结果: {x + y}"


print("执行堆叠装饰器函数:")

print(example_function(10, 20))

print()


# 理解装饰器堆叠顺序

def trace_decorator(name):

   def decorator(func):

       @wraps(func)

       def wrapper(*args, **kwargs):

           print(f"{name}: 进入")

           result = func(*args, **kwargs)

           print(f"{name}: 退出")

           return result

       return wrapper

   return decorator


@trace_decorator("装饰器A")

@trace_decorator("装饰器B")

@trace_decorator("装饰器C")

def nested_function():

   print("执行核心函数")


print("\n执行嵌套装饰器:")

nested_function()

第三部分:综合实战练习

python

# 综合实战:电商系统用户权限管理

from enum import Enum

from functools import wraps

from datetime import datetime


class UserRole(Enum):

   GUEST = 1

   CUSTOMER = 2

   VIP = 3

   ADMIN = 4

   SUPER_ADMIN = 5


class User:

   def __init__(self, username, role=UserRole.GUEST):

       self.username = username

       self.role = role

       self.created_at = datetime.now()

       self.last_login = None

   

   def login(self):

       self.last_login = datetime.now()

       print(f"{self.username} 登录成功")

   

   def __str__(self):

       return f"用户: {self.username}, 角色: {self.role.name}"


class PermissionDecorator:

   """权限装饰器工厂"""

   

   @staticmethod

   def require_role(min_role):

       def decorator(func):

           @wraps(func)

           def wrapper(user, *args, **kwargs):

               if user.role.value < min_role.value:

                   return f"权限不足! 需要 {min_role.name} 以上权限"

               return func(user, *args, **kwargs)

           return wrapper

       return decorator

   

   @staticmethod

   def require_any_role(*roles):

       def decorator(func):

           @wraps(func)

           def wrapper(user, *args, **kwargs):

               if user.role not in roles:

                   role_names = [r.name for r in roles]

                   return f"权限不足! 需要以下角色之一: {', '.join(role_names)}"

               return func(user, *args, **kwargs)

           return wrapper

       return decorator

   

   @staticmethod

   def log_operation(operation_name):

       def decorator(func):

           @wraps(func)

           def wrapper(user, *args, **kwargs):

               timestamp = datetime.now().strftime("%Y-%m-%d %H:%M:%S")

               print(f"[{timestamp}] {user.username} 执行 {operation_name}")

               try:

                   result = func(user, *args, **kwargs)

                   print(f"[{timestamp}] 操作成功")

                   return result

               except Exception as e:

                   print(f"[{timestamp}] 操作失败: {e}")

                   raise

           return wrapper

       return decorator


# 创建用户

users = {

   "guest": User("游客", UserRole.GUEST),

   "customer": User("普通客户", UserRole.CUSTOMER),

   "vip": User("VIP客户", UserRole.VIP),

   "admin": User("管理员", UserRole.ADMIN),

   "super": User("超级管理员", UserRole.SUPER_ADMIN)

}


# 业务功能类

class ECommerceSystem:

   

   @PermissionDecorator.require_role(UserRole.GUEST)

   @PermissionDecorator.log_operation("浏览商品")

   def view_products(self, user):

       return "浏览商品列表"

   

   @PermissionDecorator.require_role(UserRole.CUSTOMER)

   @PermissionDecorator.log_operation("添加购物车")

   def add_to_cart(self, user, product):

       return f"{user.username} 添加 {product} 到购物车"

   

   @PermissionDecorator.require_role(UserRole.CUSTOMER)

   @PermissionDecorator.log_operation("下单购买")

   def place_order(self, user, order_details):

       return f"{user.username} 下单: {order_details}"

   

   @PermissionDecorator.require_role(UserRole.VIP)

   @PermissionDecorator.log_operation("使用VIP折扣")

   def use_vip_discount(self, user):

       return f"{user.username} 使用VIP专属折扣"

   

   @PermissionDecorator.require_any_role(UserRole.ADMIN, UserRole.SUPER_ADMIN)

   @PermissionDecorator.log_operation("管理商品")

   def manage_products(self, user):

       return f"{user.username} 管理商品"

   

   @PermissionDecorator.require_role(UserRole.SUPER_ADMIN)

   @PermissionDecorator.log_operation("系统配置")

   def system_config(self, user):

       return f"{user.username} 进行系统配置"


# 测试系统

system = ECommerceSystem()


print("测试电商系统权限控制:")

print("=" * 60)


test_cases = [

   ("游客浏览商品", lambda: system.view_products(users["guest"])),

   ("游客下单", lambda: system.place_order(users["guest"], "商品1")),

   ("客户下单", lambda: system.place_order(users["customer"], "商品1")),

   ("VIP使用折扣", lambda: system.use_vip_discount(users["vip"])),

   ("客户使用VIP折扣", lambda: system.use_vip_discount(users["customer"])),

   ("管理员管理商品", lambda: system.manage_products(users["admin"])),

   ("VIP管理商品", lambda: system.manage_products(users["vip"])),

   ("超级管理员系统配置", lambda: system.system_config(users["super"])),

   ("管理员系统配置", lambda: system.system_config(users["admin"])),

]


for test_name, test_func in test_cases:

   print(f"\n{test_name}:")

   print("-" * 40)

   try:

       result = test_func()

       print(f"结果: {result}")

   except Exception as e:

       print(f"异常: {e}")

练习作业

作业1:实现一个购物车系统

创建一个ShoppingCart类,要求:


使用@property装饰器实现商品数量的只读属性


使用类方法创建特定类型的购物车(如打折购物车)


使用静态方法验证商品信息


作业2:创建缓存装饰器

实现一个缓存装饰器,要求:


可以设置缓存过期时间


支持不同的缓存策略(LRU、FIFO)


可以统计缓存命中率


作业3:实现验证装饰器

创建一个表单验证系统,要求:


验证用户输入的数据类型


验证数据范围(如年龄在0-150之间)


验证必填字段


作业4:综合项目 - 银行账户系统

设计一个银行账户系统,要求:


使用抽象基类定义账户接口


实现储蓄账户和信用卡账户


使用装饰器实现交易日志和权限控制


实现转账功能,需要验证余额和权限


学习要点总结

面向对象高级特性:


类方法和静态方法的区别与应用场景


@property装饰器实现属性的访问控制


抽象基类定义接口规范


装饰器核心概念:


装饰器的本质是函数/类,返回函数/类


使用@wraps保留原函数元信息


装饰器可以堆叠,执行顺序从下往上


实际应用场景:


权限验证和访问控制


性能监控和日志记录


缓存和记忆化


输入验证和格式化


最佳实践:


保持装饰器简单、专注单一功能


为装饰器编写清晰的文档


考虑装饰器的性能和副作用


在下一课中,我们将学习:


上下文管理器(with语句)


生成器和协程


异步编程基础


元编程初步


明扬工控商城

推荐阅读:

Python中级教程 第六课:高级特性与性能优化 2/2

Python中级教程 第六课:高级特性与性能优化 1/2

Python中级教程 第五课:异步编程与并发 2/2

Python中级教程 第五课:异步编程与并发 1/2

Python中级教程 第四课:上下文管理器、生成器与迭代器

Python中级教程 第三课:面向对象编程深入与装饰器

热门标签:
Python中级教程 第三课:面向对象编程深入与装饰器.docx

将本文的Word文档下载到电脑

推荐度:

下载

全部评论

请登录
产业新闻-明扬资讯网
科技资讯-明扬资讯网