内部类:
可以在一个类的内部定义其他的类,称为内部类,一般来说内部类完成的功能比较单一,代码量比较少。
在java中内部类一般分为4中:常规内部类、静态内部类、局部内部类、匿名内部类。
- 常规内部类:
常规内部类没有用static修饰且定义在在外部类类体中(也就是说定义在外部类的里面,方法的外面)。
说明:
1.可以访问外部类中的所有(包括私有)的属性的方法。
2.创建内部类的时候必须先创建外部类的对象,然后通过外部类的对象创建内部类。
语法:内部类名 内部类对象=外部类对象.new 内部类名([参数列表]);
3.外部类不能够直接访问内部类中的成员变量,如果访问必须先创建对象。
创建对象的时候按照正常创建对象的方式。
例如:
package com.bxit; /** * 内部类 * @author zhy * */ //外部类 public class Test2 { private String age="50"; /** * 内部类:在一个类中再定义一个类,就叫做内部类。 * 内部类分类4种:常规内部类,静态内部类,局部内部类,匿名内部类 * 常规内部类: * 1.可以访问外部类中的所有(包括私有)的属性的方法。 * 2.创建内部类的时候必须先创建外部类的对象,然后通过外部类的对象创建内部类。 * 语法:内部类名 内部类对象=外部类对象.new 内部类名([参数列表]); * 3.外部类不能够直接访问内部类中的成员变量,如果访问必须先创建对象。 * 创建对象的时候按照正常创建对象的方式。 */ //内部类 class Test3{ public Test3(String s) { System.out.println("内部类的构造方法"+s); } private String name; String name1="q"; public String getName() { return name; } public void setName(String name) { this.name = name; } public void print(){ System.out.println(age); } } public String getAge() { return age; } public void setAge(String age) { this.age = age; } public void print(){ //创建内部类的对象 Test3 t=new Test3("zhangsan"); System.out.println(t.name); } public static void main(String[] args) { //创建外部类的对象 Test2 test=new Test2(); //创建test对象中的内部类 Test3 test3=test.new Test3("内部类"); test3.print(); } } |
静态内部类:
与类的其他成员相似,可以用static修饰内部类,这样的类称为静态内部类。
说明:
1.静态内部类可以调用外部类中的static成员属性和方法(包括私有的)
2、如果要访问非静态的属性和方法,必须先创建外部类的对象
3.静态内部类,可以直接去创建对象,不需要通过外部类的对象去创建。
例如:
package com.bxit; /** * 静态内部类 * @author QJ * */ public class Test { private String name; public String getName() { return name; } public void setName(String name) { this.name = name; } public static void print(){ System.out.println("测试"); } /** * 静态内部类:使用static修饰的内部类 * @author QJ * 1.静态内部类可以调用外部类中的static成员属性和方法(包括私有的) * 2、如果要访问非静态的属性和方法,必须先创建外部类的对象 * 3.静态内部类,可以直接去创建对象,不需要通过外部类的对象去创建。 */ static class Test1{ private String name1; public String getName1() { return name1; } public void setName(String name1) { this.name1 = name1; } public void test(){ print();//调用静态方法 Test test=new Test(); test.setName("张三"); //setName1("zhangsan"); //System.out.println(name); } } public void print1(){ //创建静态内部类的实例 Test1 test=new Test1(); test.setName("张三"); System.out.println(test.name1); } public static void main(String[] args) { //创建静态内部类的实例 Test1 test=new Test1(); test.setName("张三"); System.out.println(test.name1); } } |
局部内部类:
在方法体或语句块(包括方法、构造方法、局部块或静态初始化块)内部定义的类成为局部内部类。
说明:
1.局部内部类可以访问外部类中的成员变量和方法。
2.局部内部类中只能去访问当前方法中的局部变量,但是不能修改,默认使用final 修饰
3.局部内部类和局部变量一样不可以使用权限修饰符进行修饰
4.局部内部类只能在包含他的方法中去创建对象,其他地方没有办法使用该类。
例如:
package com.bxit; /** * 局部内部类 * @author QJ * */ public class Test1 { /** * 局部内部类:定义在方法或者语句块中的类。 * 1.局部内部类可以访问外部类中的成员变量和方法。 * 2.局部内部类中只能去访问当前方法中的局部变量,但是不能修改,默认使用final修饰 * 3.局部内部类和局部变量一样不可以使用权限修饰符进行修饰 * 4.局部内部类只能在包含他的方法中去创建对象,其他地方没有办法使用该类。 */ private String name; public String getName() { return name; } public void setName(String name) { this.name = name; } public void print(){ int i=10; //局部内部类 class Test2{ private String name1; public String getName1() { return name1; } public void setName1(String name1) { this.name1 = name1; } public void test(){ //访问外部类的成员变量 System.out.println(name); //访问方法的局部变量 System.out.println(i); } } //创建局部内部类的对象 Test2 t=new Test2(); t.name1="zhangsan"; System.out.println(t.name1); //System.out.println(name1); } public void test2(){ //不能创建局部内部类的对象 //Test2 t=new Test2(); } public static void main(String[] args) { Test1 t=new Test1(); t.print(); } } |
匿名内部类:
定义类的最终目的是创建一个类的实例,但是如果某个类的实例只是用一次,则可以将类的定义与类的创建,放到与一起完成,或者说在定义类的同时就创建一个类以这种方法定义的没有名字的类成为匿名内部类。
说明:
声明和构造匿名内部类的一般格式如下:
new ClassOrInterfaceName(){
/*类体*/ }
1.匿名内部类可以继承一个类或实现一个接口,这里的ClassOrInterfaceName是匿名内部类所继承的类名或实现的接口名。但匿名内部类不能同时实现一个接口和继承一个类,也不能实现多个接口。如果实现了一个接口,该类是Object类的直接子类,匿名类继承一个类或实现一个接口,不需要extends和implements关键字。
2.由于匿名内部类没有名称,所以类体中不能定义构造方法,由于不知道类名也不能使用关键字来创建该类的实例。实际上匿名内部类的定义、构造、和第一次使用都发生在同样一个地方。
例如:
package com.bxit; /** * 匿名内部类:没有专门的类名 * @author QJ * 1.匿名内部类是专门为创建实例而存在的, * 当一个接口或者抽象类的实例只用一次的时候,可以考虑是用他。 * 2.匿名内部类可以继承抽象类或者实现接口, * 但是不会使用implements和 extends关键字 * 3.在匿名内部类中只能实现一个接口和继承一个类 * 4.在匿名内部类中只能访问局部变量,不可以修改局部变量。 */ public class Test3 { private String name; //实现了一个接口返回的是一个对象的引用,所以可以直接使用或将其复制给一个对象变量 public InterfaceTest in=new InterfaceTest() { @Override public void test() { System.out.println(name+"匿名内部类"); } public void test1(){ }; }; public void test(){ int i=0; //实现了一个接口 new InterfaceTest () { @Override public void test() { //i=10; System.out.println(name+"匿名内部类"+i); } }.test(); //继承了一个抽象类 new AbstractTest() { @Override public void test() { // TODO Auto-generated method stub } }; } public static void main(String[] args) { Test3 t=new Test3(); t.in.test(); } } |
类的继承中,子类拥有父类的所有属性和方法,父类的某些方法实现在子类中可能不够全面,而要求在子类中重写,这是父类经常设计为抽象类,抽象类的某些方法只有声明没有实现。子类除了继承父类的属性和方法外,每个类还包含很多其他的功能(也就是方法),这时经常把功能方法抽象为接口,接口中只声明方法,要求具体的类实现该方法。Java中每一个类只能有一个父类(包括抽象类),但是可以同时实现多个接口。