结构化
属性, 参数变量 和 局部变量Properties, Parameters and Local Variables
变量的种类
属性, 参数变量, 局部变量
1 2 3 4 5 6 7 8 9 public class Var { public int a; public void f(int b){ // ... int c; // ... }}
变量的作用域与生命周期
种类 | 生命周期 | 作用域 |
---|---|---|
属性 | 随对象生, 随对象死 | 所有方法均可访问 |
参数变量 | 方法调用时生, 调用完死 | 在声明的方法内可以访问 |
局部变量 | 变量声明时生, 碰到包含它的最近的大括号时死 | 从声明的那一行, 到包含它的最近的大括号结束 |
变量命名问题
参数和局部变量 可以跟 属性重名
其它组合 均不可以
属性默认值
新建的对象如果没有给属性赋值,属性会变为默认值
类型 | 默认值 |
---|---|
byte, short, char, int, long | 0 |
float, double | 0.0 |
boolean | false |
对象类型 | null |
this 省略规则
访问属性
访问属性应该加 this,但是可以省略
1 2 3 4 5 6 7 8 9 10 public class Cla { public int a; public void func() { // 完整写法 System.out.println(this.a); // 省略写法 System.out.println(a); }}
属性 与 局部变量 或者 参数 同名
1 2 3 4 5 6 <7 8 9 <10 11 public class Cla { public int a; public void func() { int a = 3; // 完整写法,属性 System.out.println(this.a); 0 // 不能省略,省略后是局部变量 System.out.println(a); 3 }}
访问方法
访问方法应该加 this,但是可以省略
1 2 3 4 5 6 7 8 9 10 11 12 public class Cla { public void func() { // 完整写法 this.func2(); // 省略写法 func2(); } public void func2() { }}
Getters and Setters
案例
开始
Player.java
1 2 3 4 5 public class Player { public int atk; public int def; public int hp;}
Driver.java
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 public class Driver { public static void main(String[] args) { new Driver().run(); } public void run(){ Player player1 = new Player(); Player player2 = new Player(); player1.atk = 100; player1.def = 100; player1.hp = 100; player2.atk = 100; player2.def = 100; player2.hp = 100; int damage = 200; player1.hp -= damage; player2.hp -= damage; }}
思考
上面的代码 违背了什么业务逻辑?
对 hp 进行保护
Driver.java
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19+20+21+22 23+24+25+26 27 public class Driver { public static void main(String[] args) { new Driver().run(); } public void run(){ Player player1 = new Player(); Player player2 = new Player(); player1.atk = 100; player1.def = 100; player1.hp = 100; player2.atk = 100; player2.def = 100; player2.hp = 100; int damage = 200; player1.hp -= damage; if (player1.hp < 0) { player1.hp = 0; } player2.hp -= damage; if (player2.hp < 0) { player2.hp = 0; } }}
思考
上面的代码 可以如何改进
增加 Setter
Player.java
1 2 3 4 5 6+7+8+9+10+11+12 public class Player { public int atk; public int def; public int hp; public void setHp(int hp){ if (hp < 0) { hp = 0; } this.hp = hp; }}
Driver.java
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18*19*20 21 public class Driver { public static void main(String[] args) { new Driver().run(); } public void run(){ Player player1 = new Player(); Player player2 = new Player(); player1.atk = 100; player1.def = 100; player1.hp = 100; player2.atk = 100; player2.def = 100; player2.hp = 100; int damage = 200; player1.setHp(player1.hp - damage); player2.setHp(player2.hp - damage); }}
固定格式
什么是 Getter Setter
针对属性的访问和赋值的专用方法(一套)
Setter
用于赋值
1 2 3 4 5 // 使用前player.hp = 200; // 使用后 player.setHp(200);
Getter
用于取值
1 2 3 4 5 // 使用前int value = player.hp; // 使用后int value = player.getHp();
固定格式
1 2 3 4 5 6 7 8 9 // Getterpublic 属性类型作为返回值类型 getXxxxXxx(){ return xxxxXxx;} // Setterpublic void setXxxxXxx(属性类型作为参数类型 xxxxXxx){ this.xxxxXxx = xxxxXxx;}
具体实现代码可以产生差异,但方法签名必须符合标准