Java语法糖--匿名内部类

1. 前言

匿名内部类,有的朋友觉得不好理解,其实顾名思义就可以了。

匿名,表示这个类没有名称。

内部类,表示不是一个独立的类,而是在一个类或方法内部的类。

2. 传统方式

首先我们需要面向接口编程,这个是很自然,面向接口编程提供了对现实社会模型的抽象,可以提供更高的灵活性。

传统方式下,我们通过类来实现接口,然后通过类对象来进行调用。

2.1 定义接口

举个例子,打仗需要使用武器,武器需要准备,然后发射,所以定义武器接口:

/**
 * 武器接口
 */
public interface Weapon {
    
    
	/**
	 * 准备
	 */
	public void prepare();

	/**
	 * 发射
	 */
	public void launch();
}

2.2 使用接口

当军队发起战役时,需要使用武器进行战斗:

/**
 * 战役类
 */
public class Battle {
    
    
	/**
	 * 使用武器进行战斗
	 */
	public void fight(Weapon w) {
    
    
		w.prepare();
		w.launch();
	}
}

2.3 使用实现类

OK,此时如果是现代军队,武器种类很多,有坦克、大炮、航母、飞机等等,我们可以实现各种武器,然后进行战斗。
如下示例,就是最常用的,定义类实现接口,然后通过类对象进行调用。

/**
 * 坦克武器
 */
public class Tank implements Weapon {
    
    
	@Override
	public void prepare() {
    
    
		System.out.println("坦克装填炮弹");
	}

	@Override
	public void launch() {
    
    
		System.out.println("坦克开火");
	}
	
	public static void main(String[] args) {
    
    
		Battle battle=new Battle();
		Tank tank=new Tank();
		battle.fight(tank);
	}
}

3. 使用匿名内部类

但是如果接口的实现类只使用一次,我们来定义类,并通过类对象来进行操作是比较繁琐的。

具体到上面的场景中,就是说根本没啥高科技武器,就是一群原始人用扔石头战斗。此时如果单独定义一个石头类意义不大,而且比较麻烦,所以可以直接用匿名内部类解决。

/**
 * 战役类
 */
public class Battle {
    
    
	/**
	 * 使用武器进行战斗
	 */
	public void fight(Weapon w) {
    
    
		w.prepare();
		w.launch();
	}
	public static void main(String[] args) {
    
    
		Battle battle = new Battle();
		// 使用匿名内部类
		battle.fight(new Weapon() {
    
    
			@Override
			public void prepare() {
    
    
				System.out.println("拿起石头");
			}
			@Override
			public void launch() {
    
    
				System.out.println("扔石头");
			}
		});
	}
}

注意在上面的例子中,我们并未定义Weapon接口的实现类,而是直接创建了Weapon类型的对象,同时定义了一个实现Weapon接口的匿名内部类。

注意匿名内部类同时定义了类的方法,而且接着就生成了该类型的对象,然后接着就调用了,非常简洁而方便。

如果上面的例子还不好理解的话,可以参考:

/**
 * 战役类
 */
public class Battle {
    
    
	/**
	 * 使用武器进行战斗
	 */
	public void fight(Weapon w) {
    
    
		w.prepare();
		w.launch();
	}

	public static void main(String[] args) {
    
    
		Battle battle = new Battle();
		// 使用匿名内部类
		Weapon weapon = new Weapon() {
    
    
			@Override
			public void prepare() {
    
    
				System.out.println("拿起石头");
			}

			@Override
			public void launch() {
    
    
				System.out.println("扔石头");
			}
		};
		battle.fight(weapon);
	}
}

4. 使用场景

大部分情况下,还是使用接口–实现类这样的结构。

如果仅仅是在调用时临时使用,可以不定义实现类,借助匿名内部类来快速开发。

猜你喜欢

转载自blog.csdn.net/woshisangsang/article/details/107159686