C++基础笔记-2

1-数组作为函数的形参会怎么样?int*(*a[3][4])[5]

// 分析:要定义一个数组的指针 等价于 定义一个 数组中首元素的指针
// 首先要知道数组中的元素是什么类型,然后定义出相应的指针
答:会弱化成指针,int *(*(*pa)[4])[5]

2-写一个给数组排序的函数,需要传哪些参数?

答:数组名,数组大小

3-什么是参数缺省?需要注意什么(三点)?
  • 概念:函数在定义时预先给出形参的默认值,调用时如果给出实参,则采用实参值,否则采用预先给出的默认形参值。

  • 注意:
    1. 函数的多次声明并且形参值不一样时应注意缺省形参的作用域
    2. 二义性,参数类型不匹配;明确实参的类型
    3. 参数缺省;参数不缺省
4-函数重载的注意事项?5点

​ 4-1-重载函数的形参必须不同:个数不同,类型不同,或者不同类型的顺序不同
​ 4-2-不能以形参名区分
​ 4-3-不能以返回值区分
​ 4-4-尽量不要将两个功能不同的函数定义成重载函数,避免出现误解,混淆
​ 4-5-二义性:
​ 4-5-1-参数类型不匹配;办法:明确实参的类型
​ 4-5-2-参数缺省;解决办法:参数不缺省

5-内联函数的作用?以及注意事项(四点)。
  • 作用:以代码膨胀作为代价,空间换取时间。编译时在调用处用函数体进行替换,节省了参数传递,控制转移等开销。

  • 注意:
    1. 内联函数体内不能有循环语句和switch语句

    2. 代码不能过长,最好是不超过 5 行

    3. 递归函数不能定义成内联函数

    4. 调用内联函数前,必须已经出现内联函数的定义,而不能只出现内联函数的声明

6-用宏定义实现一个返回两个数中较大数的功能。并说出与用普通函数实现的优点。
#define Max(x, y) ((x)>(y)?(x):(y)))  // (x):表示 x 是一个不可分割的整体
不同之处#define宏函数
代码长度程序在预处理时进行宏替换,代码长度增长使用函数的地方都调用同一份代码,代码长度不变
执行时间宏只在预处理时花费时间,所以执行速度较快运行时函数调用需要分配单元,保存现场,值传递和返回的过程中花费时间,所以相对较慢
参数类型宏的使用与参数类型无关参数类型必须保持一致
可调式性宏内有bug,在运行时不能断点调试函数体内有bug,运行时可以断点调试
二义性因为边界问题容易产生二义性如:#define sqrt(x) x*x, 假设x=10+1,则宏展开之后就变成了10+1*10+1函数不会因为边界问题产生二义性
递归不支持递归支持递归
访问权限在C++中宏不能访问类对象的私有成员成员函数可以访问私有成员
7-递归函数的优缺点?构成递归需要具备的条件?
  • 优点:
    • 递归算法解题通常显得简洁
    • 把问题转化为规模缩小了的同类子问题,然后递归调用函数来表示问题的解
  • 缺点:
    • 效率低
    • 系统通过栈来存储每一层的返回点,局部变量,递归次数过多容易造成栈溢出
  • 构成条件:
    • 子问题必须与原始问题为同样的事,且更为简单(简而治之的思想)
    • 不能无限制的调用本身,必须有个出口,化简为非递归状况处理
8-结构体类型变量定义的三种方式?
  • 先定义结构体,再说明结构体变量

    struct Enemy { 结构体 } ;

    Enemy em;

  • 定义结构体时说明结构体变量

    struct Enemy { 结构体 } em1, em2;

  • 直接说明结构体变量,不指定结构体名(一次性定义完变量,后面就不能再定义变量了)

    struct { 结构体 } em1, em2;

9-结构体变量用{}初始化时,需要注意什么?
  • 必须按照顺序初始化(不能有初始值) Enemy e1 = {19, “anti”};
10-结构体在内存中的存储原则(三点)?
  1. 各类数据按照一定的规则在空间上排列,而不是顺序的一个接一个排列(字节对齐)
  2. 结构体的总大小为结构体最宽基本类型的整数倍
  3. 所有变量存储在自己所占内存的整数倍上
11-枚举类型的变量赋值能用数字赋值么?要用什么赋值?
  • 不能,会报错,要用枚举元素赋值

    enum DIR {up, down, left, right};

    DIR dir;

    // dir = 1; // 这个会直接报错

    // 只能用枚举元素赋值

    dir = up;

12-联合类型变量的初始化是怎么初始化的?
  • 在声明语句中初始化联合变量时,总是初始化联合的第一个数据成员。
13-联合类型的在内存中的存储原则?
  • 联合类型是将多个数据项组织为一个整体,它们在内存中占用同一段存储单元,联合类型的变量所占用的字节长度为最长的成员的长度。
14-类和结构体中的成员的访问权限分别默认是什么类型?
  • 类默认是私有的
  • 结构体默认是公有的
  • 这也是类和结构体唯一的区别
15-构造函数与析构函数的特征?
  • 构造函数:
    1. 函数名与类名相同
    2. 无函数类型,无返回值
    3. 一个新的对象被建立时,该对象隶属类的构造函数自动被调用,对这个对象完成初始化
    4. 若类中无显示构造函数,则系统自动给出默认构造函数 <类名>(void){};
    5. 若有多个构造函数,一般它们有不同的参数表和函数体
  • 析构函数:
    1. 名称 ~类名(){};
    2. 无函数类型,无返回值,没有参数
    3. 一个类只有一个析构函数,也可以缺省
    4. 若类中无显示析构函数,则系统自动给出默认的析构函数 ~<类名>(void){}
    5. 在对象生存期结束时,包括用delete函数释放动态对象时,系统自动调用
16-构造函数与析构函数的调用次数和顺序有什么规律?
  • 构造函数与析构函数的调用次数相同

  • 先构造内部对象再构造外部对象

  • 先析构外部对象再析构内部对象

    class A {
    private:
    	int age;
    public:
    	A(int age_) { cout << 407 << " A 类带参构造函数被调用 " << endl; this->age = age_; }
    	A() { cout << 408 << "A 类的默认构造函数被调用" << endl; }
    	~A() { cout << 409 << " A 类的析构函数被调用" << endl; }
    };
    class B {
    private:
    	A a;  // 这里并不会创建对象,类的组合
    	int weight;
    public:
    	B(int age_, int weight_) :a(age) {
    		cout << 417 << " B 类的构造函数被调用" << endl;
    		this->weight = weight_;
    	}
    	~B() {
    		cout << 422 << " B 类的析构函数被调用" << endl;
    	}
    };
    int main() {
        B(22, 176);  
        // 先构造最里面的对象,然后再构造外层对象
        // 析构的时候先析构外层对象,然后再析构内层对象
    	/*
    		407 A 类带参构造函数被调用
    		417 B 类的构造函数被调用
    		422 B 类的析构函数被调用
    		409 A 类的析构函数被调用
    	*/
    }
    
17-什么是拷贝构造函数?什么时候调用?
  • 本质是构造函数,只是参数为:const 类名 &引用名 // 本类对象的常引用

  • 调用:

    • 用类的一个对象去初始化另一个对象时

      CHero  hero_0(200), hero_4(9);
      CHero  hero_1(hero_0); // 显示调用拷贝构造函数
      CHero  hero_5 = hero_4; // 隐式调用拷贝构造函数
      hero_4 = hero_0; // 此处不是调用拷贝构造函数,而是调用赋值运算符函数
      
    • 函数的形参是类的对象,调用函数时或者进行实参和形参结合时

    • 如果函数的返回值是类的对象,函数调用完成返回时

18-什么是浅拷贝?如何解决浅拷贝问题?
  • 浅拷贝不会开辟新的内存空间
  • 类中有成员变量为指针,在调用默认的拷贝构造函数,和默认的 = 赋值操作时出现的是浅拷贝
  • 重写拷贝构造函数
  • 重载 = 操作符
19-初始化类的对象有哪四种方式?要注意什么?
  • 默认初始化
    • 使用默认构造函数
  • 直接初始化
    • Gir gir(“name”, “age”);
  • 拷贝初始化
    • 通过拷贝构造函数来初始化
  • 值初始化
    • ???
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值