初始化块
代码块:
{
xxxx
}
初始化块是对构造器的补充,不能接受任何参数,用于定义类实例化生成的所有对象共有的属性,方法和内容
非静态代码块:没有static修饰的代码块
1.可以有输出语句。
2.可以对类的属性声明进行初始化操作。
3.可以调用静态和非静态的变量或方法。
4.若有多个非静态的代码块,那么按照从上到下的顺序依
次执行。
5.每次创建对象的时候,都会执行一次。且先于构造器执行
public class Person {
String name;
//构造方法
public Person(){
this.name = "liming";
System.out.println("执行的构造方法");
}
//非静态代码块
{
System.out.println("执行的非静态代码块");
}
public static void main(String[] args) {
new Person();
}
}
打印结果:
执行的非静态代码块
执行的构造方法
执行顺序:
1 类的属性默认初始化
2 执行的非静态代码块
3 执行的构造方法
public static void showAge(){
System.out.println(age);
}
static int age = 18;
//静态代码块
static{
//这里只能使用静态static修饰的属性和方法
age = 1;
showAge();
System.out.println("执行的静态代码块");
}//习惯把属性放在后面,代码块写在前面
静态代码块只执行一次。
public class Person {
String name;
static int age;
public Person(){
this.name = "liming";
System.out.println("执行的构造方法");
}
//非静态代码块
{
System.out.println("执行的非静态代码块");
}
public static void showAge(){
System.out.println(age);
}
//静态代码块
static{
//这里只能使用静态static修饰的属性和方法
age = 18;
showAge();
System.out.println("执行的静态代码块");
}
public static void main(String[] args) {
new Person();
new Person();
}
}
发现:
静态代码块只执行一次
非静态代码块,每次new对象的时候重复执行。
静态代码块:用static 修饰的代码块
1.可以有输出语句。
2.可以对类的属性声明进行初始化操作。
3.不可以对非静态的属性初始化。即:不可以调用非静态的属
性和方法。
4.若有多个静态的代码块,那么按照从上到下的顺序依次执行。
5.静态代码块的执行要先于非静态代码块。
6.静态代码块只执行一次
在实际开发中,静态代码块用的会多一些
这有什么用?
static int age=18;不就可以了吗?,为什么要在静态代码块里面赋值?
因为age 是简单的属性,换一个例子看
新加一个test方法,建立一个匿名类,alt+/ ,方法的重写。
这个是匿名类,不能new,没有构造器,所以在静态代码块内初始化!
匿名类(静态代码块的作用)
读代码:看注释!
public class Person {
String name;
static int age;
public Person(){
this.name = "liming";
System.out.println("执行的构造方法");
}
//非静态代码块
{
System.out.println("执行的非静态代码块");
}
public static void showAge(){
System.out.println(age);
}
//静态代码块
static{
//这里只能使用静态static修饰的属性和方法
age = 18;
showAge();
System.out.println("执行的静态代码块");
}
public void test() {
System.out.println("这是person里的test方法");
}
public static void main(String[] args) {
// new Person();
// new Person();
//没有名称的person的子类。没有类名,就不能构造方法
Person p = new Person() {
{
//用代码块代替构造方法
super.name = "javer";
}
@Override
public void test() {
// TODO Auto-generated method stub
System.out.println("========");
}
};
System.out.println(p.name);
p.test();//执行的是重写的方法
}
}
关键字final
final是太监,不能继承。
final
final标记的类不能被继承。提高安全性,提高程序的可读性。
String类、System类、StringBuffer类
final标记的方法不能被子类重写。
final标记的变量(成员变量或局部变量)即称为常量。名称大写,且只能被赋值一次。
static final:全局常量
抽象类
用abstract关键字来修饰一个类时,这个类叫做抽象类;
用abstract来修饰一个方法时,该方法叫做抽象方法。
抽象类不能被实例化。抽象类是用来作为父类被继承的,抽象类的子类必须重写父类的抽象方法,并提供方法体。
抽象类一定要有抽象方法,或者提供方法体(不是抽象方法了)
不能用abstract修饰属性、私有方法、构造器、静态方法、final的方法。
含有抽象方法的类必须被声明为抽象类。
代码没有报错,但是不能运行?debug发现main方法写错位置了
源代码:
public abstract class Animal {
public abstract void test();
public abstract void move();
public static void main(String[] args) {
Dog d = new Dog();
d.move();
}
}
class Dog extends Animal{
@Override
public void test() {
// TODO Auto-generated method stub
System.out.println("===");
}
@Override
public void move() {
// TODO Auto-generated method stub
System.out.println("run");
}
}
也可以新建一个Test.java,用来调用main方法。
练习:
编写一个Employee类,声明为抽象类,包含如下三个属性:name,id,salary。提供必要的构造器和抽象方法:work()。对于Manager类来说,他既是员工,还具有奖金(bonus)的属性。请使用继承的思想,设计CommonEmployee类和Manager类,要求类中提供必要的方法进行属性访问。
源代码:
/**
* 编写一个Employee类,声明为抽象类,
* 包含如下三个属性:name,id,salary。
* 提供必要的构造器和抽象方法:work()。
* 对于Manager类来说,他既是员工,还具有奖金(bonus)的属性。
* 请使用继承的思想,设计CommonEmployee类和Manager类,
* 要求类中提供必要的方法进行属性访问。
* @author jkjkjk
*
*/
public abstract class Employee {
public Employee(){
}
int id;
String name;
double salary;
//抽象方法work
public abstract void work();
}
//子类CommonEmployee
class CommonEmployee extends Employee{
/**
* set,get 方法进行属性访问。
* @param id
* @param name
* @param salary
*/
public void setCommonEmployee(int id, String name,double salary) {
//父类的用super
super.id = id;
super.name = name;
super.salary = salary;
}
public void getCommonEmployee() {
System.out.println("这是一个普通员工编号"+super.id);
System.out.println("这是一个普通员工姓名"+super.name);
System.out.println("这是一个普通员工月薪"+super.salary);
}
@Override
public void work() {
// TODO Auto-generated method stub
System.out.println("这是父类抽象方法的重写");
}
}
//子类,manage
class Manage extends Employee{
double bonus;//子类的成员变量
public void setManage(int id, String name,double salary,double bonus) {
super.id = id;
super.name = name;
super.salary = salary;
this.bonus = bonus;//本类用this
}
public void getManage() {
System.out.println("这是一个普通员工编号"+super.id);
System.out.println("这是一个普通员工姓名"+super.name);
System.out.println("这是一个普通员工月薪"+super.salary);
System.out.println("这是一个普通员工奖金"+this.bonus);
}
@Override
public void work() {
// TODO Auto-generated method stub
}
}
/**
* 实例化employee
* @author jkjkjk
*
*/
public class TestPerson {
public static void main(String[] args) {
CommonEmployee ce = new CommonEmployee();
ce.work();
ce.setCommonEmployee(007, "liming", 25000);//要求类中提供必要的方法进行属性访问。
ce.getCommonEmployee();
}
}
模板方法设计模式(TemplateMethod)
抽象类作为多个子类的通用模板,子类在抽象类的基础上进行扩展、改造,但子类总体上会保留抽象类的行为方式。
抽象类是一个大纲,抽象方法就算章节,子类就是内容