C\C++与Java中的static关键字
C\C++里面的static:
面向过程的static:
在c和c++面向过程的设计里,在全局变量前加上static关键字则可将该变量定义为一个静态全局变量,比如:
static int a;
那么c和c++中的静态全局变量有什么特点呢:
1、 变量在全局数据区分配内存(局部变量在栈内,通过new和malloc动态分配的变量在堆里);
2、 未经初始化的全局变量会被程序自动初始化为0;
3、 静态全局变量或函数在声明它的文件内是可见的,在文件外是不可见的;(可以起到保护作用)
讲讲第三点,如果我们只是在某个头文件中声明了一个普通的全局变量a,那么在引用这个头文件的时候,我们也可以通过extern关键字将这个变量引用到当前文件中;但是如果你在声明那个变量的时候就加了static关键字,那么全局变量a对于其他任何文件都是不可见的。
同样的,如果以static方式定义了一个函数,那么这个函数只在定义它的文件内可见。
面向对象的static:
在面向对象设计里面,使用static有几点要注意:
1、 静态成员函数的声明在类内要加上static关键字,但是在类外实现的时候不需要;
2、 静态成员函数没有this指针,所以不要尝试显示或隐式地在静态成员函数内引用这个指针,这种做法会导致编译期间报错。因此也就不要尝试些什么在构造函数中给静态成员变量初始化的动作了。
下面写个小例子感受一下面向对象的static:
首先定义一个头文件account.h,在头文件中定义一个类:
#pragma once class Account { public: static void reiseInterest(double var ); static double interest(){return dInterest; } //类内给出实现,语句简单,无递归,与类外实现并声明为inline函数都是相同的,均为内联函数 private: static double dInterest ; }; double Account::dInterest = 5; //静态数据成员初始化 inline void Account::reiseInterest(double var) { dInterest += var; }
接着在源文件中进行测试:
#include <iostream> #include "account.h" using namespace std; int main() { //double Account::dInterest = 5; //错误!!static关键字限制了可视域!! cout<<"The initial interest is "<<Account::interest()<<endl; Account ac1; Account ac2; ac1.reiseInterest(18); ac2.reiseInterest(17); cout<<"The current interest is "<<Account::interest()<<endl; return 0; }
运行结果如下:
Java部分:
Java中,在一个类里面,一个变量一旦声明,即使没有对变量进行初始化,它们也会获得一个默认值。不过需要注意的是,只有当变量作为一个类的数据成员被使用的时候才能确保获得初值。
所以static对于java是没有所谓赋予默认初值的说法的。
但是如果一个变量不属于任何类,比如说只是一个局部变量:
int a;
那么这个a得到的可能是任意值,而不会被自动初始化为0。
那么Java中static的作用到底是什么?
Java中的Static:
每当我们声明一个类,需要用到其中的方法和变量的时候我们都需要通过new来创建对象,再用该对象去调用具体的方法和变量。
但是有两种情况是比较特殊的:
情形1:我只想为某一特定数据分配一份存储控件,而不用去考虑究竟要创建多少对象,或者是甚至根本不去创建任何对象;
情形2:我希望某个方法不与包含它的类的任何对象关联在一起,即是,即使没有创建对象,我也能够调用这个方法。
这个时候我们就需要用到static。
下面进行一些小测试:
class StaticTest { static int a = 47; public StaticTest(){} } class StaticFun { static void Fun() { StaticTest.a++; } } public class StaticT { public static void main(String[] args) { // TODO Auto-generated method stub StaticTest st1 = new StaticTest(); StaticTest st2 = new StaticTest(); StaticTest.a++; System.out.println("st1's a is "+st1.a); System.out.println("st2's a is "+st2.a); StaticFun.Fun(); System.out.println("current a is "+StaticTest.a); System.out.println("st1's a is "+st1.a); System.out.println("st2's a is "+st2.a); } }
运行结果如下: