C++中的struct

C++之父Bjarn Stroustrup对C++语言概括的第一条就是"a better C"。struct这个关键字就来源于C。而在C++中,struct的含义已经和C中的struct不尽相同了。在C++中,用户定义类型,也就是class,拥有和内建类型一样的地位。这可以从C++中struct定义的类型在声明变量时不必再写出struct关键字看出。如

struct Foo {
    // ...
};

Foo f;

在C++程序中,人们似乎更热衷于使用class,而几乎忽略了struct的存在。实际上,struct就是成员默认为public的class(在class中,成员默认为private)。事实上以下两端代码完全等价:

代码一:

struct Foo {

    // ...

};

代码二:

class Foo {

public:

    // ...

};

那么为什么要有struct的存在呢?首先的原因自然是保持对C的兼容。原先的C代码可以不必修改就成为合法的C++代码。第二个原因(个人愚见),是为了让struct来表示抽象的数据类型以及抽象接口,而与class所表示的类的概念相区别。

struct在C中的使用方式转移到C++以后仍然是非常重要,作为一组相关的数据而存在于一个struct,说明了他们在逻辑上是相互关联的数据,同时他们被保存在struct里而不是全局变量,也是对数据的一种管理。个人认为一种很朴素的用法要取代当前很热门的get-set用法。比如

class Foo {

    int bar;

public:

    int get_bar() { return bar; }

    void set_bar(const int& b) { bar = b; }

};

这里Foo::bar是一个需要频繁存取的数据对象,它作为类Foo的私有成员存在,而通过公共接口存取。这是面向对象思想中数据封装的体现。而考虑一下这个Foo::bar是否有必要成为私有成员?没有,因为它就是一个数据,没有必要用私有类成员的思想来封装它,似乎可以看成是面向对象思想的过度滥用。等效的可以写成:

struct Foo {

    int bar;

};

然后通过普通的赋值操作来完成。这样做似乎是回到了原始时代,但没有必要用的就不要用,否则还会影响效率。

其次一个struct的应用就是来描述纯虚类,也就是后来Java语言中类似接口的东西:

struct Foo {

    virtual void Bar1() = 0;

    virtual void Bar2() = 0;

    // ...

};

使用struct可以些许节省编译器的语法分析时间:),而且能在语义上表达的更为清楚。

一般来讲,当一个类中有必要进行数据隐藏时,请用class声明,并将私有数据标记为private,公共接口标记为public;而当所有成员都有必要成为公有成员的时候,请用struct来声明它。

参考资料:

Bjarne Stroustrup - The C++ Programming Language, special edition, 2000,  Addison-Wesley Press

### C++ 中 `struct` 的使用方法和特点 #### 结构体定义与初始化 在 C++ 中,`struct` 不仅能像 C 一样作为数据集合存在,还支持成员函数、访问控制符以及继承等面向对象编程特性。下面是一个简单的例子来展示如何定义并初始化一个结构体: ```cpp #include <string> struct Person { std::string name; int age; void introduce() const { std::cout << "My name is " << name << ", I am " << age << " years old." << std::endl; } }; int main(){ // 初始化方式一:直接赋值 Person person1{"Alice", 30}; // 初始化方式二:默认构造后设置属性 Person person2; person2.name = "Bob"; person2.age = 25; person1.introduce(); person2.introduce(); return 0; } ``` 此代码片段展示了两种不同的初始化方法,并且包含了成员函数用于打印个人信息[^1]。 #### 成员函数和支持的操作符重载 除了基本的数据存储外,C++ 还允许向 `struct` 添加行为——即成员函数。这使得它可以执行特定的任务或计算。此外,还可以实现操作符重载以便更自然地处理自定义类型的实例之间的交互。 ```cpp struct Point { double x, y; Point operator+(const Point& other) const{ return {this->x + other.x, this->y + other.y}; } bool operator==(const Point& other)const{ return (this->x == other.x && this->y == other.y); } }; Point p1{1.0, 2.0}, p2{3.0, 4.0}; auto sum_p = p1 + p2; // 使用加法运算符 bool equal = (p1 == p2); // 判断两个点是否相等 ``` 这段程序说明了怎样创建带有算术运算符(`+`)和比较运算符(`==`)的简单二维坐标类[^2]。 #### 继承机制 尽管通常认为只有 `class` 支持多态性和虚函数等功能,但实际上,在 C++ 中 `struct` 同样能够参与单继承关系,默认情况下基类为公有(public),这意味着派生出来的子结构体会自动获得父级所有的公共接口。 ```cpp struct Shape { virtual double area() const = 0; // 抽象纯虚函数 }; struct Circle : public Shape { private: float radius_; public: explicit Circle(float r):radius_(r){} double area() const override final { return M_PI * pow(radius_, 2); } }; Shape* shape_ptr = new Circle(7.8f); std::cout<<shape_ptr->area()<<'\n'; // 输出圆面积 delete shape_ptr; ``` 上述案例构建了一个抽象图形基类及其具体圆形衍生版本,体现了基于 `struct` 实现继承的能力。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值