zoukankan      html  css  js  c++  java
  • C++之类的引入

    C++之类的引入

    一、结构体到类的演变

    C语法

    • 定义新的数据类型,该新的数据类型称之为结构体,成员为各种数据类型的变量。
      struct stu 
       {
         char age;
         int  greade;
       };
       stu stu1;  //用新的数据类型结构体定义变量
    

    C++语法

    • 定义新的数据类型该新的数据类型称之为类,成员不仅可以包含变量数据,还包含着方法,也称操作函数。
       class stu
       {
         char age;
         int greade;
         void operate()
            {
               cout<<"hell a new data is create<<endl";
            }
       };
       stu stu1;  //用新的数据类型类定义变量(C++这里的用类定义的变量称为对象)
    

    二、对象的定义与使用

    2.1、栈上定义对象

       //方式1、 先声明类,再定义对象
           class stu
           {
             char age;
             int greade;
             void operate()
                {
                   cout<<"hell a new data is create<<endl";
                }
           };
           stu stu1;  		//第一种定义对象的方法
           class stu stuq; //第二种定义对象的方法
    
       //方式2、声明类同时定义对象
          class stu
           {
             char age;
             int greade;
             void operate()
                {
                   cout<<"hell a new data is create<<endl";
                }
           }stu1;
    
    //方式3、没有类名,直接定义对象
      class
       {
         char age;
         int greade;
         void operate()
            {
               cout<<"hell a new data is create<<endl";
            }
       }stu1;
    

    2.2、堆上定义对象

    2.2.1、堆上普通数据类型的定义

    C语言中提供了 malloc 和 free 两个系统函数,完成对堆内存的申请和释放。而 C++则提供了两关键字 new 和 delete。

    //整形类型的定义
    int main()
    {
    	// int *p = (int*)malloc(sizeof(int));
    	int *p = new int(10); //new
    	*p = 100;
    	cout<<*p<<endl;
    	int **pp = new int *; // (int**)malloc(sizeof(int*))
    	Stu *ps = new Stu;
    	return 0;
    }
    //一维数组的定义
    int main()
    {
    	// new float [10] malloc(10*sizeof(float);
    	float *p = new float [10]{1.2,3.4};
    	for(int i=0; i<10; i++)
    	{
    		cout<<p[i]<<endl;
    	}
    	char **pp = new char *[11];
    	for(int i=0; i<10; i++)
    	{
    		pp[i] = "china";
    	}
    	pp[10] = nullptr;
    	while(*pp)
    	{
    		cout<<*pp++<<endl;
    	}
    }
    

    注意事项
    1 new/delete 是关键字,效率高于 malloc 和 free。
    2 配对使用,避免内存泄漏和多重释放。
    3 避免,交叉使用。比如 malloc 申请的空间去 delete, new 出的空间被 free。

    • 如果只是以上的功能, C中的 malloc 和 free 完全可以胜任, C++就没有必要更进一步,引入这两个关键字。重点用在类对象的申请与释放。申请的时候会调用构造器完成初始化,释放的时候,会调用析构器完成内存的清理。(见下文)

    2.2.2、堆上类对象的定义
    //1、new创建类对象例子:
    CTest* pTest = new CTest();  //pTest用来接收类对象指针。
    delete pTest;
    
    //2、不用new,直接使用类定义申明
    CTest mTest;
    
    /*此种创建方式,使用完后不需要手动释放,该类析构函数会自动执行。而new申请的对象,则只有调用到delete时再会执行析构函数,如果程序退出而没有执行delete则会造成内存泄漏。*/
    
    //3、只定义类指针
    CTest *mTest = NULL;
    mTest = new CTest();
    
    1、这跟不用new申明对象有很大区别,类指针可以先行定义后赋值,类指针只是个通用指针,在new之前不为该类对象分配任何内存空间。
    2、用普通方式创建的类对象,在创建之初就已经分配了内存空间。而类指针,如果未经过对象初始化,则不需要delete释放。
    
    
    
    //4、new对象指针作为函数参数和返回值
    
    // 下面要示意一下类指针对象作为返回值和参数使用
    class CTest 
    {  
    public:   
        int a;  
    };    
    
    class CBest 
    { 
    public:  
        int b;  
    };   
    
    CTest* fun(CBest* pBest) 
    {   
        CTest* pTest = new CTest();   
        pTest->a = pBest->b;
        return pTest;  
    }    
    
    int main() 
    {   
        CBest* pBest = new CBest();   
        CTest* pRes= fun(pBest);     
    
        if(pBest!=NULL)    
            delete pBest;   
    	if(pRes!=NULL)    
            delete pRes ;   
        return -1;  
    }
    
    • new创建对象的特点:
      1、new创建类对象需要指针接收,一处初始化,多处使用
      2、new创建类对象使用完需delete销毁
      3、new创建对象直接使用堆空间,而局部不用new定义类对象则使用栈空间
      4、new对象指针用途广泛,比如作为函数返回值、函数参数等
      5、频繁调用场合并不适合new,就像new申请和释放内存一样

    • new与非new作用域
      1、不用new:作用域限制在定义类对象的方法中,当方法结束时,类对象也被系统释放了。(安全不会造成内存系统泄漏)。
      2、用new:创建的是指向类对象的指针,作用域变成了全局,当程序结束时,必须用delete删除,系统不会自动释放,(不注意可能造成内存泄漏)。

    三、类的大小

    备注:以下内容摘自:https://www.cnblogs.com/sz-leez/p/7119232.html

    1.空类
    class A
    {
    };
    
    sizeof(A); //1
    解析:类的实例化就是为每个实例在内存中分配一块地址;每个类在内存中都有唯一的标识,因此空类被实例化时,编译器会隐含地为其添加一个字节,以作区分。
    
    2.虚函数类
    class A
    {
        virtual void Fun();
    };
    
    sizeof(A); //4
    解析:当一个类中包含虚函数时,会有一个指向其虚函数表的指针vptr,系统为类指针分配大小为4个字节(即使有多个虚函数)。
    
    3.普通数据成员
    class A
    {
        int a;
        char b;
    };
    
    sizeof(A); //8
    
    解析:普通数据成员,按照其数据类型分配大小,由于字节对齐,所以a+b=8字节。
    
    4.静态数据成员
    class A
    {
        int a;
        static int b;
    };
    
    sizeof(A); //4
    
    解析:
    1、静态数据成员存放的是全局数据段,即使它是类的一个成员,但不影响类的大小;不管类产生多少实例或者派生多少子类,静态成员数据在类中永远只有一个实体存在。
    2、类的非静态数据成员只有被实例化时,才存在。但类的静态数据成员一旦被声明,无论类是否被实例化,它都已存在。类的静态数据成员可以说是一种特殊的全局变量。
    
    5.普通成员函数
    class A
    {
        void Fun();
    };
    
    sizeof(A); //1
    解析:类的大小与它的构造函数、析构函数以及其他成员函数无关,只与它的数据成员相关。
    
    6.普通继承
    
    class A
    {
        int a;
    };
    
    class B:public A
    {
        int b;
    };
    
    sizeof(B); //8
    
    解析:普通类的继承,类的大小为本身数据成员大小+基类数据成员大小。
    
    7.虚函数继承
    
    virtual class A
    {
        int a;
    };
    
    class B:virtual public A
    {
        int b;
    };
    
    sizeof(B); //12
    

    四、类的访问权限

    • C中struct 的所有行为和属性都是 public 的(默认),此举也是为了 C++兼容 C 语言,因为 C 语言中没有权限的概念。

    • C++中的 class 是由C中struct演变而来。C++不同与C,它对外屏蔽了部分数据,只提供对外的接口。但C++中class可以指定行为和属性的访问方式,若不指定默认为 private。
    类内成员属性 类内部访问权限 对象访问权限
    public 可访问 可访问
    private 可访问 不可访问

    五、类的存储方式

    用类去定义对象时,系统会为每一个对象分配存储空间。如果一个类包括了数据和函数,要分别为数据和函数的代码分配存储空间。

    • 1、存在问题:如果用同一个类定义了 10 个对象,那么就需要分别为 10 个对象的数据和函数代码分配存储单元?

    • 问题解析:如果按上述方法,那样会大大的浪费内存空间,C++编译器在分配时只对各个对象的数据部分单独分配内存,对象的函数体分配的是同一段公用的内存。

    • 2、存在问题:既然函数代码段调用的是同一个,各对象的在调用时怎么知道当前是哪个对象在调用本函数?

    • 问题解析:C++在对象在调用公用函数时,将对象的指针(This)作为参数隐士的传递给了公用函数用来识别当前调用者对象。
  • 相关阅读:
    新基建的福音:智慧楼宇可视化监控系统引领智能化新时代
    基于 HTML5 和 WebGL 的地铁站 3D 可视化系统
    基于 HTML5 WebGL 的医疗物流系统
    基于 HTML5 的 PID-进料系统可视化界面
    基于 HTML5 Canvas 的可交互旋钮组件
    基于 HTML5 WebGL 的民航客机飞行监控系统
    基于 HTML5 Canvas 的元素周期表展示
    基于 HTML5 换热站可视化应用
    基于 HTML5 WebGL 的 3D 智慧隧道漫游巡检
    【python 爬虫】fake-useragent Maximum amount of retries reached解决方案
  • 原文地址:https://www.cnblogs.com/retry/p/9308915.html
Copyright © 2011-2022 走看看