面向对象之组合

Posted cnhyk

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了面向对象之组合相关的知识,希望对你有一定的参考价值。

TOC

一、组合介绍

耦合度越高:程序的可扩展性越低

耦合度越低:程序的可扩展性越高

1、组合的定义

组合指的是一个对象中,包含着另一个或多个对象

2、为什么要用组合

减少代码的冗余

3、如何使用组合

需求:

为老师和学生类添加打印出生年月日功能

利用继承实现

# 1、为老师类和学生类加入  year, month, day
# 2、新增打印出老师和学生的年月日的出生日期
# 通过继承来实现


# 父类
from scipy.constants import year


class People:
    def __init__(self, name, age, sex, year, month, day):
        self.name = name
        self.age = age
        self.sex = sex
        # 如果使用继承新增出生日期,需要在父类中新增(year, month, day)年月日
        self.year = year
        self.month = month
        self.day = day

    # 为其添加第二个功能,打印出生年月日
    def print_date(self):
        print(‘‘‘
        ====== 出生日期 ======
        年:%s
        月:%s
        日:%s
        ‘‘‘ % (self.year, self.month, self.day))

# 老师类
class Teacher(People):
    # 如果想通过调用父类中的init新增year, month, day,那子类中需要传入year, month, day
    def __init__(self, name, age, sex, year, month, day):
        # 以及调用父类中的super().__init__的括号中也需要传入年月日
        super().__init__(name, age, sex, year, month, day)


# 学生类
class Student(People):
    # 学生类中也需要像教师类中的形参,以便传入调用类时,括号里面的年月日
    def __init__(self, name, age, sex, year, month, day):
        super().__init__(name, age, sex, year, month, day)


# 老师对象
t1 = Teacher(‘张三‘, 27, ‘male‘, 1984, 2, 1)

# 学生对象
stu1 = Student(‘李雷‘, 20, ‘female‘, 1998, 3, 4)

print(t1.name, t1.age, t1.sex, t1.year, t1.month, t1.day)
# 调用父类中的打印出生日期
t1.print_date()
print(stu1.name, stu1.age, stu1.sex)
stu1.print_date()

利用组合实现

# 父类
class People:
    def __init__(self, name, age, sex):
        self.name = name
        self.age = age
        self.sex = sex


# 教师类
class Teacher(People):
    def __init__(self, name, age, sex):
        super().__init__(name, age, sex)


# 学生类
class Student(People):
    def __init__(self, name, age, sex):
        super().__init__(name, age, sex)


# 日期类
class Time:
    def __init__(self, year, month, day):
        self.year = year
        self.month = month
        self.day = day

    def print_time(self):
        print(‘‘‘
        ==== 出生日期 ====
        年:%s
        月:%s
        日:%s
        ‘‘‘ % (
            self.year,
            self.month,
            self.day
        ))


t1 = Teacher(‘张三‘, 39, ‘male‘)
time_obj = Time(1984, 2, 4)
# print(t1.name, t1.age, t1.sex)
# time_obj.print_time()
t1.time_obj = time_obj  # 此处相当于为t1对象中添加了time_obj对象的属性和方法
t1.time_obj.print_time()

组合练习

"""
练习需求:
    选课系统:
        1.有学生、老师类,学生与老师有属性 “名字、年龄、性别、课程”,
        2.有方法 老师与学生可以添加课程, 打印学习/教授课程。

    # 组合实现
"""


class People:
    def __init__(self, name, age, sex):
        self.name = name
        self.age = age
        self.sex = sex

    # 添加课程的功能
    def add_course(self, course_obj):  # self--->stu1
        # sut1.course_list = []
        self.course_list.append(course_obj)  # stu1.course_list.append()
        # sut1.course_list.append = [linux_obj, python_obj]

    # 打印当前对象中课程列表中的所有课程信息
    def print_all_course_info(self):  # self ---> stu1
        for course_obj in self.course_list:  # [python_obj, linux_obj]
            # 第一次循环 course_obj ---> python_obj
            # python_obj.print_course_info()
            # 相当于在调用python_obj对象中的print_course_info方法
            # 第二次循环 course_obj ---> linux_obj
            # linux_obj.print_course_info()
            # 相当于在调用linux_obj对象中的print_course_info方法
            course_obj.print_course_info()


class Teacher(People):
    def __init__(self, name, age, sex):
        super().__init__(name, age, sex)
        self.course_list = []


class Student(People):
    def __init__(self, name, age, sex):
        super().__init__(name, age, sex)
        self.course_list = []


# 定义一个课程类,里面包含了课程的名字,课程的价格,课程的时间
class ChoiceCourse:
    def __init__(self, course_name, course_price, course_time):
        self.course_name = course_name
        self.course_price = course_price
        self.course_time = course_time

    def print_course_info(self):
        print(‘‘‘
        课程名字:%s
        课程价格:%s
        课程时长:%s
        ‘‘‘ % (self.course_name,
              self.course_price,
              self.course_time))


# stu1对象拥有的属性:name,年龄,性别, course_list = []  方法:add_course(继承自父类), print_all_course_info(继承自父类)
stu1 = Student(‘韩梅梅‘, 23, ‘female‘)
# linux_obj对象拥有的属性:course_name, course_price, course_time    方法:print_course_info
linux_obj = ChoiceCourse(‘linux‘, 2000, 5)
# python_obj对象拥有的属性:course_name, course_price, course_time   方法:print_course_info
python_obj = ChoiceCourse(‘python‘, 2000, 4)

# 学生调用父类中的add_course方法添加课程
stu1.add_course(linux_obj)
stu1.add_course(python_obj)

# 学生调用父类中的打印方法
stu1.print_all_course_info()

4、总结

  • 继承
    • 继承是类与类的关系,子类继承父类的属性/方法,子类与父类是一种“从属”关系
  • 组合
    • 组合是对象与对象的关系,一个对象拥有另外一个对象中的属性/方法。




以上是关于面向对象之组合的主要内容,如果未能解决你的问题,请参考以下文章

面向对象之组合封装多态性鸭子类型

面向对象之多态

Python之面向对象的组合多态菱形问题子类中重用父类的两种方式

PHP面向对象之访问者模式+组合模式

面向对象概论之继承简述,组合简述,菱形继承简述

Python--面向对象的程序设计之多继承组合应用开发软件规范