C++基础:Stanford CS106L学习笔记 7 类

目录

7.1 类的引入

为什么需要类?

  • C 语言没有对象
  • 无法封装数据以及对这些数据进行操作的函数
  • 不具备实现面向对象编程(OOP)设计模式的能力

类将对象的数据和方法捆绑在一起!

什么是OOP?

  • 面向对象编程(Object-oriented Programming,简称 OOP)以对象为核心。
  • 侧重于类的设计与实现!
  • 类(Classes)是用户自定义的类型,可被声明为(实例化)对象!

容器(Containers)是标准模板库(STL)中定义的类!

7.2 struct VS class

类(class)包含:

  • 一系列不同类型的对象
  • 一组用于操作这些对象的函数
  • 一组对这些对象和函数的访问权限限制;

而​结构体(struct)是不设访问权限限制的类​。

使用结构体(structs)时,不存在直接的访问控制(机制)。



头文件(.h) 源文件(.cpp)
用途(Purpose) 定义接口 实现类的函数
包含内容(Contains) 函数原型、类声明、类型定义、宏定义、常量 函数实现、可执行代码
访问与编译(Access) 供多个源文件共享使用 会被编译为目标文件(object file)
示例(Example) void someFunction (); void someFunction () {...};

7.3 设计类

7.3.1 构造函数

构造函数初始化新创建对象的状态。

构造函数声明(.h文件)
cpp 复制代码
class StanfordID {
private:
    std::string name;
    std::string sunet;
    int idNumber;
public:
    // constructor for our StudentID
    // 构造函数的函数名必须与所属类的类名完全一致,且无需指定返回值类型(连void都不能写)。
    StanfordID(std::string name, std::string sunet, int idNumber);
    // method to get name, sunet, and idNumber, respectively
    std::string getName();
    std::string getSunet();
    int getID();
}
带参数的构造函数定义(.cpp文件)
cpp 复制代码
#include "StanfordID.h"
#include <string>
// 要记住命名空间(namespace),比如 ​std::(标准命名空间)。
// 在我们的 .cpp 文件中,定义成员函数时,需要将我们的类作为命名空间来使用(即通过类限定成员函数的作用域)。
StanfordID::StanfordID(std::string name, std::string sunet, int idNumber) {
    name = name;
    sunet = sunet;
    // 现在,我们还可以对用于初始化或修改成员变量的值强制执行校验(或 "检查")!
    if (idNumber > 0) idNumber = idNumber;
}
this关键字(.cpp文件)

this是指向当前类的指针。

cpp 复制代码
#include "StanfordID.h"
#include <string>
StanfordID::StanfordID(std::string name, std::string sunet, int idNumber) {
    // 使用 this 关键字来明确区分你所指代的是哪个 "name"。
    this->name = name;
    this->state = state;
    this->age = age;
}

this->x

this在幕后作为参数传递给类函数

统一初始化构造函数定义(.cpp文件)
cpp 复制代码
#include "StanfordID.h"
#include <string>
// list initialization constructor 
// 这是统一初始化语法,不过当前这种(方式)虽与之类似,但并不完全相同!
StanfordID::StanfordID(std::string name, std::string sunet, int idNumber): 
name{name}, sunet{sunet}, idNumber{idNumber} {};
函数重载------参数可有可无(.cpp文件)

默认构造函数定义与带参数构造函数定义

cpp 复制代码
#include "StanfordID.h" 
#include <string> 
// default constructor 
// 如果我们调用无参数的构造函数,就可以设置默认值!
StanfordID::StanfordID() { 
    name = "John Appleseed"; 
    sunet = "jappleseed"; 
    idNumber = 00000001; 
}

// parameterized constructor
// 编译器会根据输入的参数来判断我们想要使用哪一个(函数 / 构造函数)!
StanfordID::StanfordID(std::string name, std::string sunet, int idNumber) {
    this->name = name;
    this->state = state;
    this->age = age;
}
7.3.2 私有成员变量/函数

在.h文件中体现

7.3.3 公有成员函数(供用户使用的接口)
cpp 复制代码
#include "StanfordID.h"
#include <string>
std::string StanfordID::getName() {
    return this->name;
}
std::string StanfordID::getSunet() {
    return this->sunet;
}
int StanfordID::getID() {
    return this->idNumber;
}

设值函数返回类型为空

cpp 复制代码
#include "StanfordID.h"
#include <string>
void StanfordID::setName(std::string name) {
    this->name = name;
}
void StanfordID::setSunet(std::string sunet) {
    this->sunet = sunet;
}
void StanfordID::setID(int idNumber) {
    if (idNumber >= 0){
    this->idNumber = idNumber;
}
7.3.4 析构函数
cpp 复制代码
#include "StanfordID.h"  // 包含StanfordID类的头文件
#include <string>        // 包含string类的标准头文件
// 实现StanfordID类的析构函数
StanfordID::~StanfordID() {
    // 在此处释放/归还所有(动态分配的)数据
    delete[] my_array;  // 示例:释放动态数组my_array的内存}
    // 析构函数无需显式调用,当对象超出作用域(如离开所在代码块、程序结束)时,会被自动调用
}
7.3.5 整体例子
7.3.6 类的存储&函数的存储

Python会存关于对象类型的额外信息,来确保运行时类型检查。

但C++不会,C++只在对象中存数据。类型检查全部交给编译器。

函数并非存储在对象本身中,而是单独存储的。

7.4 类的其他性质

类别名

using实现

cpp 复制代码
class StanfordID { 
private:
    // An example of type aliasing
    using String = std::string; 
    String name; String sunet;
    int idNumber;
public:
    // constructor for our student
    StanfordID(String name, String sunet, int idNumber); 
    // method to get name, state, and age, respectively
    String getName();
    String getSunet(); 
    int getID();
}
相关推荐
思成不止于此2 小时前
【MySQL 零基础入门】DDL 核心语法全解析:数据库与表结构操作篇
数据库·笔记·学习·mysql
学编程的闹钟2 小时前
86【CSS的模块化处理】
学习
lkbhua莱克瓦242 小时前
Java进阶——IO流
java·开发语言·笔记·学习方法·io流
weixin_409383122 小时前
姜丹四方向a*寻路学习记录4 不用计算起点到目的地的f 从开始计算的是角色起点四周的格子到目的地的f
学习
浦东新村轱天乐2 小时前
2025.12.01-2025.12.07:休假回来,开始迭代vlm
笔记
im_AMBER2 小时前
Leetcode 72 数组列表中的最大距离
c++·笔记·学习·算法·leetcode
FFF团团员9092 小时前
树莓派学习笔记7:局域网的建立和程序自启动
笔记·学习
码以致用3 小时前
Kafka笔记
笔记·分布式·kafka
Dream it possible!3 小时前
LeetCode 面试经典 150_图的广度优先搜索_最小基因变化(93_433_C++_中等)(广度优先搜索(BFS))
c++·leetcode·面试·广度优先