IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> C++知识库 -> C++学习笔记 -> 正文阅读

[C++知识库]C++学习笔记

系列文章目录

1.元件基础
2.电路设计
3.PCB设计
4.元件焊接
5.板子调试
6.程序设计
7.算法学习
8.编写exe
9.检测标准
10.项目举例
11.职业规划


前言


送给大学毕业后找不到奋斗方向的你(每周不定时更新)

【牛客网】构建从学习到职业的良性生态圈
中国计算机技术职业资格网
上海市工程系列计算机专业中级专业技术职务任职资格评审


1、VS2013编程实用技巧

VS2013编程实用技巧

1、C++语言中的保留关键字:

C++中的保留关键字很多,这些关键字是C++语言默认保留的,所以作为开发人员来说不能用这些关键字来作为变量的名字等用途。用了之后就会编译报错的哦,所以大家以后实用的时候要注意一点!
关于C++中的保留关键字都有哪些详见这篇帖子:关键字

2、为什么调试的控制台的黑窗口一闪而过?

很多C++小白用户前期第一次使用VC6.0或者VS2013进行调试的时候,一般都是按F5,之后程序启动起来,黑窗口一闪而过,连程序执行的结果什么的都没看到,类似这样的情况如何操作呢?
①、getchar 法;
②、断点法;
③、Ctrl+F5 法;
④、工具栏添加快捷按钮点击法;!

3、清理工程源码,删除无用文件,大大减少工程体积,方便分享:

大家在写好了一个程序的源码之后,可能要传给别人,与好友之间分享资料。或者是自己的代码遇到了一些问题没办法解决请求好友帮忙,也要把工程源码打包给别人。或者是大家要把自己的工程源码打包之后发布到咱们VC驿站上面,但是论坛的附件是有大小限制的。如何将工程中一些没用的文件删除掉,这样无论是传递给别人或者发布到网上方便别人下载等等,都是非常不错的,那么哪些文件是没用的呢?哪些文件可以删除呢,而且还要保证工程代码的完整性,其他人收到这个工程源码之后,用VS打开即可编译生成EXE/DLL呢?下面给大家说一下:
①、工程目录下的Debug/Release文件夹都可以删除,包括两层结构;
②、工程目录下的:SolutionName.sdf、ipch文件夹 以及 *.pch 等文件都可以直接删除,大大减少体积;
备注:VC6.0的话有个 *.ncb 文件也可以删除。
③、如果不想让VS在工程目录中生成②的文件,可以按照如下设置:
工具(T)->选项(O)…->文本编辑器->C/C+±>高级->回退位置->
始终使用回退位置->True
回退位置已在使用时,不警告->True
回退位置->留空
经过以上设置之后,VS会把 sdf、pch 等相关文件生成在系统的临时目录中,从而不生成在工程目录中,所以以后打包的时候就方便了,不用每次都清理

2、类的声明

C的面向过程和C++的面向对象
类的声明

1、类类型的声明:

C++中声明一个类类型跟声明一个结构体类型很像。例如,咱们之前讲解的声明一个结构体的类型如下:

struct Student
{
    string name;
    int num;
    char sex;
    int age;
};

一个学生的结构体类型Student,包含学生的一些属性,如:姓名、学好、性别、年龄。基于这个结构体类型我们改一下,改成生成一个类类型:

class Student
{
    string name;
    int num;
    char sex;
    int age;
};

大家看到了吗?声明一个学生的类类型和声明一个学生的结构体类型很像很像,表面上看就差了一个关键字:struct 和 class.

备注:这里面在给大家说说有关属性和方法的名字的问题。
class类中的name,num,sex 之类的按照咱们上节课的只是可以叫做属性,print_name 这个函数呢,可以叫做行为或者方法。
这里面交给大家一些更通用的叫法:name,num,sex 之类的又可以叫做成员变量,print_name 可以叫做成员函数。

2、成员访问限定符:

C++针对类的成员,设定了三种方式的访问限定符:public、private、protected(用的不多)
public:意为共有的,公开的,公用的 成员,既可以被本类中的成员函数引用,也可以被类的作用域的其他函数所引用,即从类的外部是可以调用的;
例如,我家的房子就好比是一个类,如果来客人了,那么我可能招呼客人到客厅,这个客厅就是public类型的成员,外部可以访问,客人也可以到客厅中喝水,看电视等等;

private:意为私有的,私生的 成员,只能被本类的成员函数所引用,类外部不能调用(友元类可以,这个以后说明),
例如,我家的房子就好比是一个类,卧室就是private类型的成员,是一个相对隐私的地方。如果来客人了,我不希望客人访问我的卧室,除非经过我的允许(让成员函数去访问);

protected:意为受保护的成员,不能被类外访问,这点类似private,但是可以被派生类的成员函数访问,有关派生类的说明,以后会讲解。

附:在 class 中,public、private、protected 可以出现多次,也没有先后顺序之分,例如:

class Student
{
public:
    string name;
    int num;
    int age;

private:
    char sex;

public:
    void print_name()
    {
        cout << "name = " << name << endl;
    }
};

3、如何决定成员变量及成员函数的访问权限:

一般情况下,如果不希望外界访问本类的成员变量,那么就可以把成员变量都声明为私有的。但是有个前提必须提供可以访问的接口函数,不然一个类的所有成员都是private私有的话就没有意义了,相当于闭关锁国一样,不跟任何外界打交道,这点肯定不行。比如在Student这个类中,如果把sex性别这个成员变量设置为私有的,那么Student类就应该提供可以修改或者读取sex成员变量的成员函数,并且这个函数是public的,不然外界想要知道sex变量的值就没办法获取了。大家说是不是?

当然,也可以把一些成员设置为私有的,但是不对外提供修改的接口,因为可能这个属性或者成员变量对于类对象来说可能不想被外面知道或者修改,比如,这个学生是否脚臭,这个属性对别人有意义吗?鞋一穿上之后谁也不知道你脚臭不臭,只有自己知道,而且自己知道就够了。外界不需要知道。我也没熏到你,对不对?我也没在公共场合拖鞋,对不对?

还有一种情况就是将成员函数声明为私有的,这说明这个私有的成员函数只能被该类的其他成员函数所调用,是作为辅助的接口函数的,是在类的内部使用,不对外公开。例如:
在这里插入图片描述

4、struct 和 class 关键字的区别:

上面已经说过了,在C++中已经对struct进行了扩充,不仅可以声明成员变量,还可以声明成员函数,class关键字本身就是从struct发展而来的,所以struct支持的,class都支持。那么在C++中他们有什么异同呢?
最重要的一个区别就是:class默认的成员访问限定符是private,struct默认的成员访问限定符是public.

在这里插入图片描述

3、类的成员函数

类的成员函数

1、类的普通成员函数:

类的普通成员函数跟普通的函数没什么太大的区别,也都是有参数的类型和形参,还有返回值之类的,唯一的区别就是必须由该类的实例化对象去调用。
这里面为什么强调是类的普通成员函数呢,难道还有不普通的吗?当然有,那就是类的静态成员函数,这个以后再做讲解!

2、inline 内联函数:

之前给大家讲解过普通的全局函数,刚刚又给大家讲解了类的成员函数,这里面又出来个inline内联函数是个什么东西呢?给大家讲解一下!
实际上inline内联函数是从C语言的宏发展而来的。例如,程序main函数中直接执行以下三行代码:

int a = 5;
++a;
int b = a + 3;

和将该三行代码封装成一个函数让main函数调用的开销是完全不一样的。函数调用的过程中需要将参数压栈等等操作,详情可以看下这篇帖子:
https://www.cctry.com/thread-289482-1-1.html

C语言中可以用宏来实现一些相对简单的函数,例如:

#define MAX_NUM(x, y) (x > y ? x : y)

调用的时候代码可以这样写:

int ret = MAX_NUM(3, 6);

调用的时候感觉 MAX_NUM 像个函数,但是他是个宏,宏跟函数的区别是,在编译阶段就将宏的代码展开直接替换调用宏的地方。所以省去了函数调用的压栈、出栈等开销。所以执行效率方面要比函数高。
但是宏定义写起来比较难度倒是不大,就是麻烦一些,而且代码的可阅读性会变差。所以C++中引入了inline内联函数这么个东西,用inline关键字声明的函数,可以在调用的时候,将函数的代码直接嵌入到调用的地方,所以大大的减少了函数调用的开销,提高了效率。

例如:

class Student
{
public:
    string name;
    int num;
    int age;

private:
    char sex;
    inline int max_num(int x, int y)
    {
        return x > y ? x : y;
    }

public:
    int get_max_num(int a, int b, int c)
    {
        int max_ab = max_num(a, b);
        return max_ab > c ? max_ab : c;
    }

    void print_name()
    {
        cout << "name = " << name << endl;
    }
};

备注1:默认情况下,在类体中直接定义/实现的函数,C++会自动的将其作为inline内联函数来处理,所以类似上面的代码:max_num、get_max_num、print_name 函数都会被看成是 inline 内联函数。而在类体外部定义的函数C++则会将其作为普通的类的成员函数来处理。那么如何在类体外部定义成员函数呢,接着往下看!

备注2:也不是把所有的函数都声明成 inline 就是好事儿,如果函数的执行体很大,很耗时,那么就不适合作为 inline 内联函数,只有当函数的执行体很小,只有几行代码,而且会被频繁的调用的时候才适合作为 inline 内联函数的。这点还请大家谨记。

3、类的声明和实现分离:

一般情况下,可以把类的声明和实现都写在一起.但是,随着类的功能越来越多,类中的成员变量和成员函数也是越来越多,类的代码长度就越来越大,而且随着长度的增加不太便于阅读,层次不清晰,让人一眼望过去就一大面。那怎么办呢?
好的做法就是将类的声明和成员函数的定义分离开,成员函数的声明放在类的内部,实现或者定义放在类的外部,加上作用域限定一下就行,类似下面这样:
在这里插入图片描述

4、使用多文件分离类的声明和实现:

通过上面的学习,我们已经成功的将类的声明与实现分离了,但是呢,代码还是在一个文件中,不够清晰。接下来给大家介绍一种更贴近我们平时编程开发的方法:将类的声明放到 .h 头文件中,将类的实现放到 .cpp 实现文件中,谁要使用这个类,就 include 包含 .h 类的头文件就可以啦!接下来视频演示一下如何进行 h 和 cpp 的分离,具体看视频教程演示。
(模板类的代码必须都放在 .h 文件中,没办法实现 .h 和 .cpp 的分离,这个以后会讲解的)

这里面也可以直接使用VS2013添加类向导的方式来添加类到我们的工程中。起好类的名字之后,VS2013会自动添加该类的 h 头文件和 cpp 文件到我们的工程中,具体看教程演示!
所以,大家以后从一些开源网站,或者从咱们VC驿站下载的一些开源的类来使用的时候,作者都是提供关于该类的一个 .h 文件和一个 .cpp 文件。
在这里插入图片描述

在这里插入图片描述
在这里插入图片描述

在这里插入图片描述

4、this指针

this指针
什么情况下需要手动加上this:

class Student
{
public:
    char name[50];
    int num;
    int age;

public:
    void set_age(int age)
    {
            age = age;
    };
};

大家看到了吗?set_age 函数的参数名字和成员变量的名字一样,都是age,那么这样的情况下,大家说说成员变量的age是否能真的赋值呢?大家不妨先把视频教程暂停,自己实践下,之后再继续播放教程!
不同的编译器可能实现的结果不同,但是在我们的vs2013中,答案是否定的。成员变量age并没有通过函数 set_age 被正确的赋值。那么这个时候怎么办呢?解决的方法是将 set_age 函数改成如下:

void set_age(int age)
{
    this->age = age;
};

5、类的构造函数

类的构造函数

1、什么是构造函数?

构造函数就是解决上面的问题而存在的。构造函数是一种特殊的成员函数,与其他成员函数不同,不需要用户来主动调用它,构造函数会在对象被建立时自动被调用的。作用就是用来处理对象的初始化操作。

2、构造函数的注意事项:

①、构造函数的名字必须与类名同名,不能随意命名,这样的话才能让编译器认为该函数是构造函数,而不是类的普通成员函数;
②、构造函数不具有任何类型,不返回任何值,连 void 都不是;
③、构造函数不需要用户调用,也不应该被用户调用,它是对象建立的时候自动被系统调用,用来初始化刚刚建立的对象的;
④、如果用户没有定义自己的类的构造函数,那么系统会自动生成一个默认的构造函数,只不过该构造函数的函数体是空的,也就是什么都不做。

6、函数的重载与默认参数

函数的重载与默认参数

1、函数重载的由来:

在平时的编程过程中,一个函数可能就实现一个功能,多个功能就需要多个函数。但有时候多个功能之间很像,只是一些细节有差异,那么类似这样的功能能不能写成一个函数呢?例如,要求2个数中比较大的数,这两个数的类型有时候是int类型,有时候是float类型,那么我们按照之前的写法应该是这样封装函数:

int max_int(int a, int b);
float max_float(float a, float b);

所以,用户在调用的时候就要根据不同的参数类型,调用不同名字的函数,如果要求两个int类型的数中的比较大的就要调用 max_int,如果要求两个float类型的数中的比较大的就要调用 max_float,能不能叫一个名字呢?让系统自己去适配到底调用哪个?答案是可以的。例如:

int max_num(int a, int b);
float max_num(float a, float b);

实际上这就是函数的重载。
C++允许同一函数名定义多个函数,这些函数的参数类型和个数可以不相同,而且至少要有一个不相同,如果都相同的话就会报重复定义的链接错误了。使一个函数名可以多用。

2、函数重载的要求:

重载函数的参数个数、参数类型、参数顺序 三者中必须至少有一种不同(不然会产生调用疑惑)。函数的返回值类型可以相同也可以不同。

另外,在跟大家说一下,函数的重载一般都是功能相近,或者功能类似的函数进行重载,不能把一些功能相差很大,或者完全不相关的函数叫同一个名字,语法上是没有错误,但是违背函数重载设计的初衷啦。

3、函数的默认参数:

那么现在呢,我想让这个函数更灵活一些,有的时候我只想求最大值,有的时候我只想求最小值,有的时候我同时求最大值和最小值。
void get_min_max(int src[], int arr_len, int* max_v, int* min_v);
能不能不让我每次都得定义两个 int 类型的变量用来接收数组中的最大值和最小值。我需要最大值就给我最大值,我需要最小值就给我最小值。如何才能办到呢?

4、函数默认参数的注意事项:

①、在函数声明的时候指定,如果没有函数的声明则可以放在函数的定义中,但是声明和定义只能选一个;
②、从第一个有默认值的参数开始,后面的所有参数必须都有默认值才行;
③、调用的时候如果要自定义非第一个默认值的参数,那么前面所有的参数都要明确的写上默认值才行;
④、从使用角度来说函数的默认值比重载更方便,从函数内部实现角度来说比函数的重载更复杂。

7、类的构造函数与析构函数

类的构造函数与析构函数

1、构造函数中的参数初始化表:

用这种方式实现的构造函数体积小,代码显得更简洁,显得比较NB哈!那么怎么用呢,咱们举个例子:

class CStudent
{
public:
    char name[50];
    char sex;
    int num;
    int age;

    CStudent(char* pname, char t_sex, int t_num, int t_age);
};
CStudent::CStudent(char* pname, char t_sex, int t_num, int t_age) :sex(t_sex), num(t_num), age(t_age)
{
    strcpy(name, pname);
}

2、析构函数:

析构函数也是一个在类中跟构造函数类似的特殊功能的成员函数。只不过它的作用是与构造函数相反,是在对象的生命周期结束的时候会被自动调用的。在C++中析构函数的名字跟类名相同,并且前面带上一个取反的符号~,表达的意思也就是跟构造函数的过程相反。

默认情况下,如果类的设计者没有自己定义析构函数,那么编译器会自动为该类生成一个默认的析构函数,只不过函数体是空的,也就是什么都没做。所以,如果需要在对象被删除的时候做一些操作的话,那么就得自己定义析构函数喽。

以下几种情况会自动调用析构函数:
①、如果在一个函数中定义了一个局部变量的对象,那么当这个函数执行结束时也就是该变量对象生命周期结束的时候,所以析构函数会被自动调用;
②、全局变量或者static类型的变量,他们的生命周期一般是在程序退出的时候,这时候该对象的析构函数才会被调用;
③、如果是用new操作符动态的创建了一个对象,只有当用delete进行释放该对象的时候,析构函数才会被调用;
在这里插入图片描述

3、析构函数的特点:

析构函数不返回任何值,没有函数类型,也没有任何函数的参数。由于上面这些特点,所以析构函数不能被重载,所以说一个类可以有多个构造函数,但只能有一个析构函数。

  C++知识库 最新文章
【C++】友元、嵌套类、异常、RTTI、类型转换
通讯录的思路与实现(C语言)
C++PrimerPlus 第七章 函数-C++的编程模块(
Problem C: 算法9-9~9-12:平衡二叉树的基本
MSVC C++ UTF-8编程
C++进阶 多态原理
简单string类c++实现
我的年度总结
【C语言】以深厚地基筑伟岸高楼-基础篇(六
c语言常见错误合集
上一篇文章      下一篇文章      查看所有文章
加:2022-11-05 00:06:35  更:2022-11-05 00:11:22 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年5日历 -2024/5/19 6:21:42-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码