一、static 关键字的概念
1、理解:静态的
2、我们希望 某些特定数据,在内存空间里只有一份(节省内存空间)
3、static 规定的属性、方法 供所有对象使用
二、static关键字的使用
1、修饰对象:属性、 方法、 代码块、 内部类。
2、修饰属性:静态变量(类变量)
属性,按是否使用static修饰,又分为:静态属性 vs 非静态属性(实例变量)
- 实例变量, 我们创建了类的多个对象,每个对象都独立拥有一套类中的非静态属性。当修改其中一个对象的非静态属性时,不会导致其他对象中相同的属性值改变
- 静态变量, 我们创建了类的多个对象,多个对象共享同一个静态变量。当通过某一个对象修改静态变量时,会导致其他对象中的该属性也改变。
说明
- 静态变量随着类的加载而加载,归类所有。静态变量的加载,早于对象的加载
- 静态变量可以通过 “ 类.静态变量 ” 的方式调用
- 实例变量随着对象的加载而加载,归对象所有。
- 由于类只会加载一次,所以静态变量在内存中也值存在一份(存在方法区的静态域中)
-
o 类变量 实例变量
-
类 Yes NO
-
对象 Yes Yse
-
⑥ 静态属性举例 System.out \ Math.PI
3、修饰方法:静态方法
随着了类的加载而加载,可以通过 “ 类.静态方法 ” 的方式调用
-
o 静态方法 非静态方法
-
类 Yes NO
-
对象 Yes Yse
静态方法中不能调用 非静态的方法或属性,只能调用 静态的方法和属性
非静态方法中 既可以调用 静态的方法和属性, 又可以调用 非静态的方法或属性。
注意:
- 静态方法中不能使用 this 关键字 和 super 关键字
- 关于静态方法和静态属性的使用 , 可以从 属性和方法 生命周期的角度取理解。
4、开发中,如何确定一个 属性 是否要声明为static的?
属性是可以被多个对象所共享的,不会随着对象的不同而不同
类中的 常量 常常声明为static 例如Math.PI
5、开发中,如何确定一个 方法 是否要声明为static的?
操作静态属性的方法,通常设置为static的
工具类中的方法, 习惯上声明static ,比如,Math , Arrays ,Collections
三、完整示例
1、示范
public class StaticTest {
public static void main(String[] args) {
Chinese c1 = new Chinese();
c1.name = "姚明";
c1.age = 40;
c1.nation = "中国";
System.out.println(c1.nation);//中国
Chinese c2 = new Chinese();
c2.name = "马龙";
c2.age = 30;
c2.nation = "Chinese";
System.out.println(c2.nation);//Chinese,c1给natio赋值时,也给c2赋值了
System.out.println("Chinese.nation");//可以直接永 “ 类.静态属性 ” 的方式调用
System.out.println("c1.show()");
System.out.println("Chinses.eat()");//可以直接永 “ 类.静态方法 ” 的方式调用
}
}
class Chinese{
String name;
int age;
static String nation;//静态变量
public void show(){
System.out.println("我是一个中国人");
}
public static void eat(){ //静态方法
System.out.println("中国人吃中餐");
}
//编译不通过
/* public static void info(){
System.out.println("名字时"+ name);
}
*/
}
2、习题1
编写一个类实现银行账户的概念,包含的属性有“帐号”、“密
码”、“存款余额”、“利率”、“最小余额”,定义封装这些
属性的方法。 账号要自动生成。编写主类,使用银行账户类,输入、输出3个储户的上述信息。
考虑:哪些属性可以设计成static属性。
public class Account {
public static void main(String[] args) {
Customer c1 = new Customer(123,1000);
Customer c2 = new Customer(123,2000);
Customer c3 = new Customer(123,3000);
//打印信息
c1.getInfo();
c2.getInfo();
c3.getInfo();
}
}
class Customer{
private int id;
private int keys;
private double balance;
private static double rate = 0.12;
private static double minBalance = 100;
private static int init = 1001;//用于自动生成id
//构造器
public Customer() {
this.id = init;
init++;
}
public Customer( int keys, double balance) {
this();
this.keys = keys;
this.balance = balance;
}
//取值赋值
public int getId() {
return id;
}
public int getKeys() {
return keys;
}
public double getBalance() {
return balance;
}
public static double getRate() {
return rate;
}
public static double getMinBalance() {
return minBalance;
}
public static int getInit() {
return init;
}
//打印信息
public void getInfo(){
System.out.println("账号:"+id+",密码:"+keys+",余额:"+balance);
}
}
3、习题2
public class CircleTest {
public static void main(String[] args) {
Circle c1 = new Circle();
Circle c2 = new Circle();
//非static,init2每创建一个对象就重新赋值
System.out.println(c1.getId2());//1001
System.out.println(c2.getId2());//1001
//static,init在类加载时就已经赋值,static声明的属性被所有对象共享
System.out.println(c1.getId());//1001
System.out.println(c2.getId());//1002,static的作用
System.out.println(c1.total);//2,计数,调用了该类多少次
System.out.println(c2.total);//2,计数,调用了该类多少次
}
}
class Circle{
private double radius;
private int id;
private int id2;
public Circle(){
id = init++;//id自动加1
id2 = init2++;
total++;
}
public Circle(int id){
this();//调用空参构造器,方便计数
this.id = id;
}
public int getId() {
return id;
}
public int getId2() {
return id2;
}
//使用static
private static int init = 1001;
static int total = 0;
//不使用static
private int init2 = 1001;
public double findArea(){
return Math.PI*radius*radius;
}
}