Java-内部类

tech2023-08-23  124

/* 如果一个事物的内部包含另一个事物,那么这就是一个类内部包含另一个类。 例如:身体和心脏的关系。 又如:汽车和发动机的关系 分类: 1.成员内部类 2.局部内部类 (包含匿名内部类) 成员内部类的定义格式: 修饰符 class 外部类名称 { 修饰符 class 内部类名称{ //... } //... } 注意:内用外,随意访问;外用内,需要借助内部类对象。 ========== 如何使用成员内部类?有两种方式: 1.间接方式:在外部类的方法中使用内部类,然后main知识调用外部类的方法 2.直接方式:公式: 类名称 对象名 = new 类名称(); 【外部类名称.内部类名称 对象名 = new 外部类名称().new 内部类名称();】 */ public class Body{ //外部类 public class Heart {//成员内部类 //内部类的方法 public void beat(){ System.out.println("心脏跳动"); System.out.println("我叫:"+name); //正确 } } //外部类的成员变量 private String name; //外部类的方法 public void methodBody(){ System.out.println("外部类的方法"); //Heart heart = new Heart(); //heart.beat(); new Heart().beat(); //匿名对象 } public String getNmae(){ return name; } public String setName(String name){ this.name = name; } } public class Demo01InnerClass{ public static void main(String[] args){ //间接方式 Body body = new Body(); //外部类的对象 //通过外部类的对象,调用外部类的方法,里面间接在使用内部类Heart body.methodBody(); System.out.println("=============="); //直接方式: //公式为: Body.Heart heart = new Body().new Heart(); heart.beat(); } }

内部类的重名变量访问:

/* 如果出现了重名现象,那么格式为:外部类名称.this.外部类成员变量名 */ public class Outer{ int num = 10; //外部类的成员变量 public class Inner{ int num = 20 ; // 内部类的成员变量 public void method(){ int num = 30; //内部类成员方法的局部变量 System.out.printlln(num); // 局部变量,就近原则 30 System.out.printlln(this.num); //内部类的成员变量 20 System.out.printlln(Outer.this.num); //外部类的成员变量 10 } } } public class Demo02InnerClass{ public static void main(String[] args){ //外部类名称.内部类名称 对象名 = new 外部类名称().new 内部类名称(); Outer.Inner obj = new Outer().new Inner(); obj.methodInner(); } }

局部内部类定义:

/* 如果一个类是定义在一个方法内部的,那么这就是一个局部内部类。 “局部”:只有当前所属的方法才能使用它,出了这个方法就不能使用了 定义: 修饰符 class 外部类名称{ 修饰符 返回值类型 外部类方法名称(){ class 局部内部类名称{ //... } } } */ public class Outer{ public void methodOuter(){ class Inner{//局部内部类 int num = 10; public void methodInner(){ System.out.println(num); //10 } } Inner inner = new Inner(); inner.methodInner(); } } public class DemoMain{ public static void main(String[] args){ Outer obj = new Outer(); obj.methodOuter(); } }

类的权限修饰符: public > protected > (default) >private 定义一个类的时候,权限修饰符规则: 1.外部类:public (default) 2.成员内部类: public protected (default ) private 3.局部内部类:什么都不能写

局部内部类的final问题:

/*局部内部类,如果希望访问所在方法的局部变量,那么这个局部变量必须是【有效final的】 备注:从Java8 开始,只要局部变量事实不变,那么final关键字可以省略 原因: 1.new出来的对象在堆内存中 2.局部变量只跟着方法走,在栈内存中 3.方法运行结束之后,立刻出栈,局部变量会立刻消失。 4.new出来的对象会在堆当中持续存在,直到垃圾回收消失。 */ public class MyOuter{ public void methodOuter(){ int num = 10; //所在方法的局部变量 class MyInner{ public void methodInner(){ System.out.println(num); } } } }

匿名内部类:

/* 如果接口的实现类(或者是父类的子类)只需要使用唯一的一次。 那么这种情况下就可以省略掉该类的定义,而改为使用【匿名内部类】。 匿名内部类的定义格式: 接口名称 对象名 = new 接口名称(){ //覆盖重写所有抽象方法 }; 对格式“new 接口名称(){...}”进行解析: 1.new代表创建对象的动作 2.接口名称就是匿名内部类需要实现哪个接口 3.{...}这才是匿名内部类的内容 另外还要注意: 1.匿名对象类,在【创建对象】的时候,只能使用唯一一次。 如果希望多次创建对象,而且类的内容一样的话,那么就必须使用单独定义的实现类了。 2.匿名对象在【调用方法】的时候,只能调用唯一一次 如果希望同一个对象,调用多次方法,那么必须给对象起个名字 3.匿名内部类是省略了【实现类/子类】,但是匿名对象是省略了【对象名称】 强调:匿名内部类和匿名对象不是一回事!!! */ public interface MyInterface{ puclic abstract void method1(); //抽象方法 public abstract void method2(); } public class MyInterfaceImpl implements MyInterface{ @override public void method1(){ System.out.println("实现类覆盖重写了方法!111"); } @override public void method2(){ System.out.println("实现类覆盖重写了方法!222"); } } public class DemoMain{ public static void main(String[] args){ //MyInterfaceImpl impl = new MyInterfaceImpl(); //impl.method(); //多态 //MyInterface obj = new MyInterfaceImpl(); //obj.method(); //使用匿名内部类,但不是匿名对象,对象名称就叫objA MyInterface objA = new MyInterface(){ @override public void method1(){ System.out.println("匿名内部类实现了方法111-A"); } @override public void method2 (){ System.out.println("匿名内部类实现了方法222-A"); } }; objA.method1(); objB.method2(); System.out.println("==========="); //使用了匿名内部类,而且省略了对象名称,也是匿名对象 new MyInterface(){ @override public void method1(){ System.out.println("匿名内部类实现了方法111-B"); } @override public void method2(){ System.out.println("匿名内部类实现了方法222-B"); } }.method1(); //因为匿名对象无法调用第二次方法,所以需要再创建一个匿名内部类的匿名对象 new MyInterface(){ @override public void method1(){ System.out.println("匿名内部类实现了方法111-B"); } @override public void method2(){ System.out.println("匿名内部类实现了方法222-B"); } }.method2(); } }

类作为成员变量类型:

//游戏当中的游戏类 public class Hero{ private String name; //英雄名字 private Weapon weapon; //英雄武器 private int age; //英雄的年龄 public Hero(){ } public Hero(String name, Weapon weapon, int age){ this.name = name; this.weapon = weapon; this.age = age; } public void attack(){ System.out.println("年龄为:"+age+"的"+name+"正在用"+weapon.getCode()+"攻击敌方。"); } public String getName(){ return name; } public String setName(String name){ this.name = name; } public String getWeapon(){ return weapon; } public String setWeapon(String weapon){ this.weapon = weapon; } public int getAge(){ return age; } public int setAge(int age){ this.age= age; } } public class Weapon{ private String code; //武器代号 public Weapon(){ } public Weapon(String code){ this.code = code; } public String gedCode(){ return code; } public String setCode(String code){ this.code = code; } } public class DemoMain{ public static void main(String[] args){ //创建一个英雄角色 Hero hero = new Hero(); //为英雄起一个名字,并且设置年龄 hero.setName("盖伦"); hero.setAge(20); //创建一个武器对象 Weapon weapon = new Weapon("多兰剑"); //为英雄配备武器 hero.setWeapon(weapon); //年龄为20的盖伦用多兰剑攻击了敌方 hero.attack(); } }

接口作为成员变量类型:

public class Hero{ private String name; // 英雄名称 private Skill skill; //英雄技能 public Hero(){ } public Hero(String name, Skill skill){ this.name = name; this.skill = skill; } public void attack(){ System.out.println("我叫"+name+",开始释放技能:"); skill.use();//调用接口中抽象方法 System.out.println("释放技能完成"); } public String getName(){ return name; } public String setName(String name){ this.name = name; } public Skill getSkill(){ return skill; } public Skill setSkill (Skill skill){ this.skill= skill; } } public interface Skill{ void use(); //释放技能的抽象方法 } public class SkillImpl implements Skill{ @override public void use(){ System.out.println("biu~biu~biu~"); } } public class DemoGame{ public static void main(String[] args){ Hero hero = new Hero(); hero.seName("艾希"); //设置英雄名称 //设置英雄技能 //hero.setSkill(new SkillImpl); 使用单独定义的实现类 //还可以改成使用匿名内部类 /*Skill skill = new Skill(){ @override public void use(){ System.out.pirntln("pia~pia~pia"); } }; hero.setSkill(skill );*/ //进一步简化,同时使用匿名内部类和匿名对象 hero.setSkill(new Skill(){ @override public void use(){ System.out.println("biu~pia~biu~pia"); } }); hero.attack(); } }

接口作为方法的参数、返回值:

/* java.util.list是ArrayList所实现的接口。 */ import java.util.ArrayList; import java.util.List; public class DemoInterface{ public static void main(String[] args){ //左边是接口名称,右边是实现类名称,这就是多态写法 List<String> list = new ArrayList<>(); List<String> result = addNames(list); for(int i = 0; i < result.size(); i++){ System.out.println(result.get(i)); } } public static List<String> addNames(List<String> list){ list.add("aaa"); list.add("bbb"); list.add("ccc"); list.add("ddd"); return list; } }
最新回复(0)