C++中static应用详解

1 首先介绍一下 :关于程序的内存分配

 <1> 栈 : 由编译器自动分配内存,存放函数的参数值,局部变量等,操作方式类似于数据结构中的栈。

 <2> 堆 : 由程序员自己分配,若程序不释放,一般在程序结束时由os释放。  比如说new 之类的,类似于数据结构中的链表
 <3> 全局区:    全局变量和静态变量都是存储在这一块的,包括静态局部变量和静态全局变量。初始化过的放在一块,没有初始化的放在另一块。程序结束后由系统释放。
 <4> 文字常量区,常量字符串存放的区域,程序结束后由系统释放。
一种是保存在栈区, char name5[20] = "fengkewei";
         或 char name1[] = "fengkewei";
        一种保存在文字常量区, 即 char *name = "fengkewei";
        一种保存在全局区(静态区)(下次有机会再说。。。)
       最后一种保存在堆区,即用malloc, alloc, realloc 分配内存分配的区域,可由程序员自身分配和释放

<5>  代码区 :存放函数的二进制代码


2 static在面向过程中的作用
  <1> 静态全局变量
       在全局变量前加上staic,和全局变量的区别是:
  1> 全局变量在可以其他文件中使用,加上extern就可以
  2>  静态全局变量 作用域是在当前文件,在其他文件中可以定义相同的名称的变量不会冲突
  
<2> 静态局部变量
        1>静态局部变量在执行到该对象的声明出时,首次被初始化,以后的函数调用不会再进行初始化
  2>
静态局部变量一般在声明处初始化,如果没有初始化,会被程序自动初始化为0
3》依然存放在全局区,知道程序运行结束,由os收回

<3>  静态函数:
          在函数的返回类型前面加上static 。与普通函数的区别是,它只能在声明的文件中使用,在其他文件中不能使用,在其他文件中有相同的函数名,不会冲突
    static void fn();

 
 3 static 在面向对象中作用
   <1> 静态数据成员
 1>公共(public)静态数据成员可被类的外部访问,保护(protected)或私有(private)静态数据成员只可被类的内部访问。
    2> 访问方式
              方式一:<类对象名>.<静态数据成员名>
      方式二:<类类型名>::<静态数据成员名>
3>  静态数据成员的初始化方式:
              <数据类型><类名>::<静态数据成员名>=<值>
4>与全局变量的区别
            (一)静态数据成员没有进入程序的全局名字空间,因此不存在与程序中其它全局名字冲突的可能性;   
            (二)可以实现信息隐藏。静态数据成员可以是private成员,而全局变量不能;
 
5> 特点:
(一)对于非静态数据成员,每个类对象都有自己的拷贝。而静态数据成员被当作是类的成员。无论这个类的对象被定义                     了多少个,静态数据成员在程序中也只有一份拷贝,由该类型的所有对象共享访问。也就是说,静态数据成员是该                     类的所有对象所共有的。对该类的多个对象来说,静态数据成员只分配一次内存,供所有对象共 用。所以,静态数据成员                   的值对每个对象都是一样的,它的值可以更新;
(二)静态数据成员存储在全局数据区。静态数据成员定义时要分配空间,所以不能在类声明中定义。语句int                                                   Myclass::Sum=0;是定义静态数据成员;
(三)静态数据成员和普通数据成员一样遵从public,protected,private访问规则;
(四)因为静态数据成员在全局数据区分配内存,属于本类的所有对象共享,,即在没有产生类的实例时,我们就可以操                               作它;
           (五)在静态成员函数和非静态成员函数中都可以使用
   <2> 静态成员函数
        在.h文件中定义的时候加上static,但是在实现的实现的时候前面并不需要加static关键字。
与普通函数相比,静态成员函数由于不是与任何的对象相联系,因此它不具有this指 针。无法访问属于类对象的非静态数据                 成员,也无法访问非静态成员函数,它只能调用其余的静态成员函数或者静态成员变量。
        主要特点如下:
 1> 在类外实现的时候不加static关键字。   
         2> 静态成员函数之间可以相互访问,包括静态成员函数和静态成员变量,
 3> 静态成员函数因为不具有this指针,因此不能访问非静态成员和非静态成员函数
 4> 非静态成员函数可以访问静态成员函数和静态成员变量
 5> 类类型名>::<静态成员函数>

 4 关于静态成员函数和静态成员变量的实例 

#include <iostream.h>  
  class Myclass  
  {public:  
  Myclass(int a,int b,int c);  
  static void GetSum();/声明静态成员函数  
  private:  
  int a,b,c;  
  static int Sum;//声明静态数据成员  
  };  
  int Myclass::Sum=0;//定义并初始化静态数据成员  
  Myclass::Myclass(int a,int b,int c)  
  { this->a=a;  
  this->b=b;  
  this->c=c;  
  Sum+=a+b+c; //非静态成员函数可以访问静态数据成员  
  }  
  void Myclass::GetSum() //静态成员函数的实现  
  {// cout<<a<<endl; //错误代码,a是非静态数据成员  
  cout<<"Sum="<<Sum<<endl;  
  }  
  void main()  
  { Myclass M(1,2,3);  
  M.GetSum();  
  Myclass N(4,5,6);  
  N.GetSum();  
  Myclass::GetSum();  
  }  


   5 注意:
     静态数据成员是静态存储的,所以必须对它进行初始化。
   静态成员初始化与一般数据成员初始化不同:
   初始化在类体外进行,而前面不加static,以免与一般静态变量或对象相混淆;
   初始化时不加该成员的访问权限控制符private,public等;
   初始化时使用作用域运算符来标明它所属类;

   所以我们得出静态数据成员初始化的格式:

6 补充1:

  

typedef  struct  CAMERAOBJINFO
{
                  int  CameraID;
                  int  priority;
                  char  IpAddress[64];
                  char  CameraVender[64];
                  char  CameraType[64];
                  char  ServerIP[64];
                  char  ConfigType[64];
                  char  Resolution[32];
                  HdIpCamContext * pCameraObj;
} CameraObjInfo ;

class  CameraList
{
public :
                CameraList();
                ~CameraList();
public :
                  static  std:: list  < CameraObjInfo > CamList;
            

};
在.cpp中初始化

std:: list <  CameraObjInfo >  CameraList  ::CamList;

上面的这个CamList就会一直存在,我们在整个工程中都可以使用其中的数据。

   

7 补充2:

4.★静态数据成员的类型可以是所属类的类型,而普通数据成员则不可以。普通数据成员的只能声明为 所属类类型的 指针或引用。举例如下: 

class base{ 
public : 
static base _object1;//正确,静态数据成员 
base _object2;//错误 
base *pObject;//正确,指针 
base &mObject;//正确,引用 
};


8 补充3:

 

二,静态成员函数  (没有this指针,只能调用静态成员变量,不能调用普通的成员变量 )
静态成员函数没有什么太多好讲的。 

1.静态成员函数的地址可用普通函数指针储存,而普通成员函数地址需要用 类成员函数指针来储存。举例如下: 
class base{ 
static int func1(); 
int func2(); 
}; 

int (*pf1)()=&base::func1;//普通的函数指针 
int (base::*pf2)()=&base::func2;//成员函数指针 


2.静态成员函数不可以调用类的非静态成员。因为静态成员函数不含this指针,包括普通成员函数和普通成员变量。

静态成员可以被普通成员函数使用。

3.静态成员函数不可以同时声明为 virtual、const、volatile函数。举例如下: 
class base{ 
virtual static void func1();//错误 
static void func2() const;//错误 
static void func3() volatile;//错误 
}; 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值