C++设计模式——UML类图

一、UML 类图元素

1.1 类的表示

在UML中,类表示为一个矩形框,分为三个区域。

  • 第一区域是类名。
  • 第二区域列出属性。
  • 第三区域列出方法。
1.2 关系的表示

UML类图中有多种类型的关系:

  • 关联(Association)
  • 聚合(Aggregation)
  • 组合(Composition)
  • 继承(Inheritance)或泛化(Generalization)
  • 依赖(Dependency)
  • 实现(Realization)

二、符号与访问权限

  • 公共成员:用 + 表示
  • 私有成员:用 - 表示
  • 受保护成员:用 # 表示

三、从代码到类图

3.1 绘制简单的类

我们以一个示例代码为模型,这个模型涉及到学生、课程、教师、和一个图书馆。:

#include <string>
#include <vector>

// 基类(父类)Person
class Person {
public:
    Person(std::string name): name(name) {}
    virtual void showName() { /*...*/ }  // 虚函数
private:
    std::string name;
};

// 子类 Student
class Student : public Person {
public:
    Student(std::string name, int studentID): Person(name), studentID(studentID) {}
    void enrollCourse(class Course*); // 单项关联
    virtual void showName() override { /*...*/ }  // 覆写虚函数
private:
    int studentID;
    std::vector<class Course*> courses;  // 自关联
};

// 子类 Teacher
class Teacher : public Person {
public:
    Teacher(std::string name, int teacherID): Person(name), teacherID(teacherID) {}
    void assignCourse(class Course*);
private:
    int teacherID;
};

// Course 类
class Course {
public:
    Course(std::string name): name(name) {}
    void setTeacher(Teacher*);  // 单项关联
private:
    std::string name;
    Teacher* teacher;  // 双向关联
    std::vector<Student*> students;  // 双向关联
};

// Library 类
class Library {
public:
    Library(std::vector<class Book*> books): books(books) {}
private:
    std::vector<class Book*> books;  // 聚合关系
};

// Book 类
class Book {
public:
    Book(std::string title): title(title) {}
};

// School 类
class School {
public:
    School(std::vector<Student*> students, Library* library): students(students), library(library) {}
private:
    std::vector<Student*> students;  // 组合关系
    Library* library;  // 组合关系
};
3.2 继承关系

如果一个类继承自另一个类,那么在UML中,两者之间用一条带有空心箭头的直线连接。箭头从子类指向父类。

  • UML 符号:一个空心三角形箭头从子类指向基类。
  • 意义:子类继承基类的所有属性和方法。在代码中,这通常通过 extends(Java)、:(C++)等关键字实现。
  • 例子:在一个学校模型里,TeacherStudent 都是 Person 类的子类,继承了 Person 的属性和方法。
3.3 关联关系

一个类作为另外一个类的子类即为关联关系

3.3.1 单项关联
  • UML 符号:一个箭头从一个类指向另一个类。
  • 意义:一个类知道另一个类的信息,并与之交互,但反过来则不然。
  • 例子:在一个订单系统里,Order 类有一个指向 Customer 类的指针或引用,表示这个订单属于哪个客户,但 Customer 类不需要知道具体的 Order
3.3.2 双向关联
  • UML 符号:一条直线连接两个类,没有箭头或两端都有箭头。
  • 意义:两个类都知道对方,并可能互相交互。
  • 例子:在一个社交网络模型里,一个 User 类可能有一个朋友列表,其中包括其他 User 实例的引用。反之亦然,那些 User 实例也有一个包含原 User 实例的朋友列表。
3.3.3 自关联
  • UML 符号:一条箭头从一个类指回到同一个类。
  • 意义:类的实例与同类的其他实例有某种关系。
  • 例子1:在一个组织图模型里,一个 Employee 类可以有一个“经理”字段,该字段是 Employee 类的另一个实例。
  • 例子2:链表关系,指向自己类型
3.4 聚合与组合关系
3.4.1 聚合
  • UML 符号:一个空心菱形箭头从“整体”指向“部分”。
  • 意义:一个类是另一个类的一部分,但两者具有各自的生命周期。
  • 例子:在一个学校模型里,School 类可能有多个 Classroom 实例,但 Classroom 也可以单独存在。
3.4.2 组合
  • UML 符号:一个实心菱形箭头从“整体”指向“部分”。
  • 意义:一个类是另一个类的一部分,并且两者有相同的生命周期。
  • 例子:在一个机体模型里,Car 类有多个 Wheel 实例。当 Car 实例被销毁时,其 Wheel 实例也会被销毁。
3.5 依赖关系

在本示例代码中没有显示,但通常如果一个类使用了另一个类的方法或属性,那么这通常表示为依赖关系。在UML中,依赖关系表示一个类依赖于另一个类的定义。这通常是一个相对较弱的关系,并且通常表示为一个带箭头的虚线。

在代码中,依赖关系可能表现为以下几种形式:

在UML类图中, ReportGenerator 类画出两条带箭头的虚线,分别指向 DatabaseReport,表示依赖关系。

  • 一个类的方法使用了另一个类的对象。
  • 一个类的方法接受另一个类的对象作为参数。
  • 一个类的方法创建并返回另一个类的对象。
  • class Database {
    public:
        // ... 省略
    };
    
    class Report {
    public:
        // ... 省略
    };
    
    class ReportGenerator {
    public:
        ReportGenerator(Database& db): db(db) {}
    
        Report generate() {
            // 使用了 Database,因此依赖于 Database
            // 创建了一个 Report 对象,因此依赖于 Report
            Report report;
            // ... 省略代码
            return report;
        }
    
    private:
        Database& db;
    };
    

    在这个例子中:

  • ReportGenerator 依赖于 Database,因为它的 generate 方法需要访问 Database
  • ReportGenerator 依赖于 Report,因为它的 generate 方法创建并返回了一个 Report 对象。
3.6 虚函数

在UML类图中,抽象类的名称通常会用斜体表示。如果一个C++类中包含至少一个纯虚函数(pure virtual function),那么这个类就是抽象的。

 四、绘制类图

 

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值