C++类与对象(1)

1,结构体到类过渡

c++兼容c语言,结构用法可以继续使用,同时struct也升级成了类。

struct Stack {
    //成员变量
    int* a;
    int top;
    int capacity;
    //成员函数
    void Init() {
        a = nullptr;
        top = capacity = 0;
    }
    void push(int x) {

    }
};

既可以用结构体的方式去访问成员变量,也可以用类的的方式去访问成员变量。

2,类的定义

(1)class 类名{主体},主体包含成员变量,和成员函数

(2)访问限定符(三种):public(共有),protected(保护),private(私有)

访问限定符一般作用到下一个访问限定符结束或者遇到“}”类结束

在类中,成员的默认访问限定符是私有的,所以如果不写访问限定符,类中的成员函数是无法使用的。而在结构体中,成员的默认访问限定符是共有的。

(3)类的声明和定义可以分离:

例如:

stack.h//声明部分

class Stack {
private:
    int* a;//数组的地址
    int top;//下一个元素的下标
    int capacity;//容量

public:
    void Init();
    void push(int x);
    int Top();
    
};

//定义部分

#include"stack.h"
#include <exception>

需要在类域中寻找变量,所以需要加 Stack::
void Stack::Init() {
    a = nullptr;
    top = capacity = 0;
}
void Stack::push(int x) {
    if (top == capacity) {
        size_t newcapacity = capacity == 0 ? 4 : capacity * 2;
        a = (int*)realloc(a, sizeof(int) * newcapacity);//realloc申请空间
        capacity = newcapacity;
    }
    a[top++] = x;
}
int Stack::Top() {
    return a[top - 1];
}

注意:直接在类里面定义,会默认为内联函数,不会生成符号表

(4)类的实例化

类中的成员变量相当于声明部分,并没有分配空间,这时就需要定义开空间,也称为对象的实例化。成员变量会在对象中存储一份,但成员方法在公共代码区中。

(5)类的大小

class Date1{//类不占内存的空间
private:
    int _year;//声明
    int _month;
    int _day;
public:
    void Inti(int year, int month, int day) {
         _year = year;
         _month = month;
         _day = day;
    }

};

Date d;

cout << sizeof(Date) << endl;//12
cout << sizeof(d) << endl;//12

类的大小或者说对象的大小看的是成员变量的类型和个数,且遵循内存对齐规则,所以上述对象的大小为12(3*4)

例1:

class A {//4byte
    int a;
    void add() {
    }
};

例2:

class A1 {//内存对齐规则、8byte
    int a;
    char b;
    void add() {
    }
};

例3:class B {//1byte表示占位表示对象存在过
    void add() {
    }
};

class C {//1byte
};

(6)this指针:

编译器在调用成员函数是,会有一个隐藏的this指针

例如:

void Inti(int year, int month, int day) {
      _year = year;
       _month = month;
       _day = day;
    }

Date d;
d.Inti(2024, 9, 9);

而编译器处理后为:

void Inti(Date* this,int year, int month, int day) {
         this->_year = year;
         this->_month = month;
         this->_day = day;
    }

Date d;
d.Inti(&d,2024, 9, 9);

但是自己写代码时,不能写成把this作为参数传递,但在类里面可以使用,比如: this->_year = year;这样的写法是可以的

总结:this在实参和形参位置不可以显示的写,但是在类里面可以显示的用,this作为形参存在栈里面,vs里面存在寄存器里面

3,构造函数

构造函数:特殊的成员函数

1,函数名与类名相同
2,无返回值
3,对象实例化时,自动调用
4,构造函数可以重载

例1:class Date {//类不占内存的空间
private:
    int _year;//声明
    int _month;
    int _day;

public:
    //无参数的构造函数
    Date() {
        _year = 1;
        _month = 1;
        _day =1;
    }

//有参数的构造函数

    Date(int year, int month, int day) {
        _year = year;
        _month = month;
        _day = day;
    }
    */
    void Print() {
        cout << _year << " " << _month << " " << _day << endl;
    }
};

类中的两个构造函数两者结合一下(缺省参数);
    Date(int year=1, int month=1, int day=1) {
        _year = year;
        _month = month;
        _day = day;
    }

例2:class Stack {
private:
    int* a;
    int top;
    int capacity;

public:
    Stack() {
        a = nullptr;
        top = capacity = 0;
    }
   
    void push(int x) {
        if (top == capacity) {
            size_t newcapacity = capacity == 0 ? 4 : capacity * 2;
            int* tmp = (int*)realloc(a, sizeof(int) * newcapacity);
            if (tmp == nullptr) {
                perror("realloc fail");
                exit(-1);
            }
            if (tmp == a) {
                cout << capacity <<"本地扩容"<< endl;
            }
            else {
                cout << capacity << "异地扩容" << endl;
            }
            a = tmp;
            capacity = newcapacity;
        }
    
        a[top++] = x;
    }
    int Top() {
        return a[top - 1];
    }
    void Pop() {
        assert(top>0);
        top--;
    }
    void Destroy() {
        free(a);
        a = nullptr;
        top = capacity = 0;
    }

Stack s1(1000);
for (int n = 0;n < 1000;n++) {
    s1.push(n);
}在这种明确知道自己想要的空间的情况下,会不断扩容,本地扩容还好,异地扩容会非常的复杂,未了避免这种情况,我们可以写成以下这种代码:

Stack(size_t n=4) {
    if (n == 0) {
        a = nullptr;
        top = capacity = 0;
    }
    else {
        a = (int *)malloc(sizeof(int) * n);
        if (a == nullptr) {
            perror("realloc fail");
            exit(-1);
        }
        top =  0;
        capacity = n;
    }
}//当你知道自己要的空间大小,这个构造函数可以减少扩容

如果你不传入参数,他会自动调用,并且空间大小初始化为4

1,不写构造函数时,编译器会自动生成,如果写了,编译器就不会提供了
2,内置类型成员不会处理(有些编译器会处理为0)(声明部分可以给缺省值)
3,对于自定义类型的成员才会处理,会去调用这个成员的构造函数,一般情况都需要我们写构造函数,决定初始化数值

4,默认构造函数,只有一个。注意:无参构造函数,全缺省构造函数,自动生成的构造函数,都默认为构造函数
总结:但是如果成员变量都是自定义类型,可以不进行初始化

4,析构函数

析构函数:
1,在类名前加 ~
2,没有参数没有返回值
3,只有一个析构函数,若没有显示定义,会自动生成一个默认的析构函数,析构函数不能重载
,内置类型成员不会处理,对于自定义类型的成员才会处理
4,在对象销毁时,自动调用析构函数

    void Destroy() {
        free(a);
        a = nullptr;
        top = capacity = 0;
    }可以写成以下代码:
    
 
~Stack() {
        free(a);
        a = nullptr;
        top = capacity = 0;
    }
 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/diannao/9176.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【科普系列】到底什么是语义通信?语义通信跟现有通信有什么区别?

语义通信&#xff1a;信息传输的未来 在探讨什么是语义通信之前&#xff0c;我们先回顾一下传统的通信方式。传统通信&#xff0c;如电话、电视或因特网&#xff0c;主要关注的是如何高效、准确地传输信号或数据。例如&#xff0c;无论是语音通话还是文件传输&#xff0c;传统…

哈希题目总结

以下列举了可以用哈希方法&#xff08;包括但不限于用HashMap和HashSet&#xff09;的题目&#xff0c;实质上是把东西丢给这些数据结构去维护。请注意有些题目中用哈希是最优解&#xff0c;有些题目中不是最优解&#xff0c;可以自行探索其时间复杂度和空间复杂度的区别&#…

C++ 基础 输入输出

一 C 的基本IO 系统中的预定义流对象cin和cout: 输入流&#xff1a;cin处理标准输入&#xff0c;即键盘输入&#xff1b; 输出流&#xff1a;cout处理标准输出&#xff0c;即屏幕输出&#xff1b; 流&#xff1a;从某种IO设备上读入或写出的字符系列 使用cin、cout这两个流对…

什么是HTTP?

什么是HTTP&#xff1f; HTTP基本概念HTTP 是什么&#xff1f;HTTP 常见的状态码有哪些&#xff1f;HTTP 常见字段有哪些&#xff1f; HTTP特性HTTP/1.1 的优点有哪些&#xff1f;HTTP/1.1 的缺点有哪些&#xff1f; HTTP基本概念 HTTP 是什么&#xff1f; HTTP 是超文本传输…

设计模式(2)——工厂方法模式

目录 1. 摘要 2. 需求案例(设计一个咖啡店的点餐系统) 2.1 咖啡父类及其子类 2.2 咖啡店类与咖啡类的关系 3. 普通方法实线咖啡店点餐系统 3.1 定义Coffee父类 3.2 定义美式咖啡类继承Coffee类 3.3 定义拿铁咖啡继承Coffee类 3.4 定义咖啡店类 3.5 编写测试类 4. 简…

故障——蓝桥杯十三届2022国赛大学B组真题

问题分析 这道题纯数学&#xff0c;考察贝叶斯公式 AC_Code #include <bits/stdc.h> using namespace std; typedef pair<int,double> PI; bool cmp(PI a,PI b){if(a.second!b.second)return a.second>b.second;return a.first<b.first; } int main() {i…

Java毕设之基于springboot的医护人员排班系统

运行环境 开发语言:java 框架:springboot&#xff0c;vue JDK版本:JDK1.8 数据库:mysql5.7(推荐5.7&#xff0c;8.0也可以) 数据库工具:Navicat11 开发软件:idea/eclipse(推荐idea) 系统详细实现 医护类型管理 医护人员排班系统的系统管理员可以对医护类型添加修改删除以及…

2024年大学生三下乡社会实践活动投稿注意事项

随着2024年夏季的热浪一同涌来的,是我校一年一度的“大学生三下乡”社会实践活动。作为一名积极参与其中的大学生,我满怀激情地投身于这项旨在促进农村发展的公益行动中。然而,当活动圆满落幕,轮到我承担起向各大媒体投稿、传播实践成果的重任时,却遭遇了一系列意想不到的挑战,…

端口占用解决方法

1、查询端口 打开cmd命令提示符窗口&#xff0c;输入以下指令查询所有端口 netstat -ano //查询所有端口 netstat -ano|findstr 8080 //查询指定端口 2、杀死进程 taskkill /t /f /im 进程号(PID)

【Ansible】ansible-playbook剧本

playbook 是ansible的脚本 playbook的组成 1&#xff09;Tasks&#xff1a;任务&#xff1b;通过tasks 调用ansible 的模板将多个操作组织在一个playbook中运行 2&#xff09;Variables&#xff1a;变量 3&#xff09;Templates&#xff1a;模板 4&#xff09;Handles&#xf…

车载测试系列:入行车载测试分享

车载测试前景如何&#xff1f; 软件定义汽车时代的发展趋势&#xff0c;随着控制器自主开发力度的加强&#xff0c;作为V流程中必备环节&#xff0c;车载测试工程师岗位需求会越来越多&#xff1b;控制器集成化&#xff0c;功能集成程度越来越高&#xff0c;对于测试工程师的知…

【前端每日基础】day2 const var const的区别

var: 在早期的 JavaScript 中&#xff0c;var 是声明变量的唯一方式。它有以下特点&#xff1a; var 声明的变量是函数作用域&#xff08;function-scoped&#xff09;&#xff0c;而不是块作用域&#xff08;block-scoped&#xff09;&#xff0c;这意味着它们在整个函数内部都…

度小满——征信报告图建模

目录 背景介绍 发展趋势 技术演进 图在金融风控领域中的演进 度小满图机器学习技术体系 案例 征信报告介绍 征信报告图建模

Vuex 和 Pinia 两个状态管理模式的区别

Pinia和Vuex一样都是是vue的全局状态管理器。其实Pinia就是Vuex5&#xff0c;只不过为了尊重原作者的贡献就沿用了这个看起来很甜的名字Pinia。&#xff08;实际项目中千万不要即用Vuex又用Pinia&#xff0c;不然你会被同事‘’请去喝茶的‘’。 一、安装&#xff08;常用命令安…

JavaScript百炼成仙自学笔记——13

函数七重关之六&#xff08;“new”一个函数&#xff09; 看个代码&#xff1a; function hello(){console.log(this); } 1、this&#xff1a;也是JavaScript中的一个关键字&#xff0c;永远指向当前函数的调用者 解释一下,有两层意思&#xff1a; ①this要嘛不出现&#…

Vue 组件参数传递:多个参数 vs 单个对象

在Vue开发中&#xff0c;我们经常需要在组件之间传递数据。当涉及到传递多个参数时&#xff0c;我们可以选择将这些参数分开传递&#xff0c;也可以将它们整合到一个对象中传递。那么在这两种方式中&#xff0c;哪种更好呢&#xff1f;让我们来探讨一下。 多个参数传递的优缺点…

深入理解 Linux 文件系统与动静态库

目录 一、Linux 文件系统中的 inode 二、软硬链接 三、动静态库 在 Linux 系统中&#xff0c;文件系统和动静态库是非常重要的概念。本文将带大家深入了解这些内容&#xff0c;让你在技术之路上更进一步。 一、Linux 文件系统中的 inode 何为文件系统&#xff1f;对计算机中…

通用型产品发布解决方案(基础环境搭建)

文章目录 1.项目技术栈和前置技术2.创建Linux平台1.需求分析2.安装Virtual Box1.BIOS里修改设置开启虚拟化设备支持&#xff08;f2 或f10&#xff09;2.任务管理器 -> cpu 查看虚拟化是否开启3.卸载方式4.安装6.1.265.管理员身份运行&#xff0c;选择安装位置6.一直下一步&a…

PHPStudy 访问网页 403 Forbidden禁止访问

涉及靶场 upload-labd sqli-labs pikachu dvwa 以及所有部署在phpstudy中的靶场 注意&#xff1a;一定要安装解压软件 很多同学解压靶场代码以后访问报错的原因是&#xff1a;电脑上没有解压软件。 这个时候压缩包看起来就是黄色公文包的样子&#xff0c;右键只有“全部提取…

大厂Java面试题:MyBatis是如何进行分页的?分页插件的实现原理是什么?

大家好&#xff0c;我是王有志。 今天给大家带来的是一道来自京东的关于 MyBatis 实现分页功能的面试题&#xff1a;MyBatis是如何进行分页的&#xff1f;分页插件的实现原理是什么&#xff1f;通常&#xff0c;分页的方式可以分为两种&#xff1a; 逻辑&#xff08;内存&…