接口定义:接口时抽象方法与全局常量的集合。子类实现接口时,用关键字implements实现。
定义一个接口:
interface Person{
public static final String name = "葵葵";//全局常量
public abstract void getInfo();//抽象方法
}
接口特点:
1.接口中所有方法都必须是抽象的,默认修饰符:public abstract
2.接口中的成员变量默认为:public static final
3.子类可以实现多个接口,同时要覆写接口父类中的所有抽象方法。
4.接口可继承接口,可多继承。
5.接口无法直接实例化对象,只能通过子类实现。
6.接口可向上转型成它的任意接口类型。
7.接口中没有构造方法,因为接口中所有方法都是抽象方法。
8.接口中只允许public权限(属性、方法),可直接省略不写。
接口的应用:(工厂设计模式)
葵葵想买一台电脑,目前她看上了电脑A、电脑B:
//定义一个抽象产品接口
interface Computer{
void printComputer();
}
//实现一个具体产品:电脑A
class ComputerA implements Computer{
@Override
public void printComputer() {
System.out.println("这是电脑A,4500元");
}
}
//实现一个具体产品:电脑B
class ComputerB implements Computer{
@Override
public void printComputer() {
System.out.println("这是电脑B,4000元");
}
}
//客户端
public class Client{
public void buyComputer(Computer computer){
computer.printComputer();
}
public static void main(String[] args){
Client client = new Client();
//如果葵葵象买电脑A
client.buyComputer(new ComputerA());
//如果她想买电脑B
client.buyComputer(new ComputerB());
}
}
如果葵葵又看上了电脑C,那么我们不得不去客户端修改代码,让客户端支持电脑C。很明显,这样做影响了其他部分。
如果我们将实例化具体类的的的代码从客户端抽离,这样还会影响到其他部分吗?
简单工厂模式:
我们可以定义一个生产电脑的工厂,客户需要什么类型的电脑,输入型号就可以获取到电脑信息。将类的实例化交给工厂。
//定义一个抽象产品接口
interface Computer{
void printComputer();
}
//实现一个具体产品:电脑A
class Computer1 implements Computer{
@Override
public void printComputer() {
System.out.println("这是电脑A,4500元");
}
}
//实现一个具体产品:电脑B
class Computer2 implements Computer{
@Override
public void printComputer() {
System.out.println("这是电脑B,4000元");
}
}
//定义一个生产电脑的工厂
class ComputerFactory{
public static Computer getComputer(String type){
Computer computer = null;
if(type.equals("电脑A")){
computer = new Computer1();
}
if(type.equals("电脑B")){
computer = new Computer2();
}
return computer;
}
}
public class Client{
public static void main(String[] args){
Client client = new Client();
Scanner sc = new Scanner(System.in);
System.out.println("请输入您想要的电脑型号:");
String type = sc.nextLine();
Computer computer = ComputerFactory.getComputer(type);//工厂生产的电脑
client.buyComputer(computer);
}
public void buyComputer(Computer computer){
computer.printComputer();
}
}
虽然简单工厂模式下,类的实例化交给工厂,易于解耦。但如果要添加具体产品,我们不得不取修改工厂,违反了面向对象编程的开闭原则。
工厂方法模式:
定义一个生产抽象电脑的工厂,让工厂子类取实例化对象具体生产什么产品。
//定义一个抽象产品接口
interface Computer{
void computerPrint();
}
//定义一个具体产品:电脑A
class ComputerA implements Computer{
@Override
public void computerPrint() {
System.out.println("这是电脑A,国产,价格:4500元");
}
}
//定义一个具体产品:电脑B
class ComputerB implements Computer{
@Override
public void computerPrint() {
System.out.println("这是电脑B,4000元");
}
}
//定义一个工厂接口
interface ComputerFactory{
Computer factory();
}
//定义一个生产电脑A的工厂
class ComputerAFactory implements ComputerFactory{
@Override
public Computer factory() {
return new ComputerA();
}
}
//定义一个生产电脑B的工厂
class ComputerBFactory implements ComputerFactory{
@Override
public Computer factory() {
return new ComputerB();
}
}
public class Client{
public static void main(String[] args){
Client client = new Client();
//如果葵葵想买电脑A,让电脑A工厂生产产品
ComputerFactory computerFactory = new ComputerAFactory();
client.buyComputer(computerFactory.factory());
//如果她想买电脑B
ComputerFactory computerFactory1 = new ComputerBFactory();
client.buyComputer(computerFactory1.factory());
}
public void buyComputer(Computer computer){
computer.computerPrint();
}
}
工厂方法模式下,客户必须知道都有哪些具体的工厂类。如果要新增产品,需要创建相应的产品类和工厂类实现抽象产品接口和抽象工厂接口,不许用修改原来的代码。这同样需要修改工厂,依然违背了面向对象编程的开闭原则。
抽象工厂模式:
如果工厂生产的产品不止一个,此时用抽象方法模式就行不通了。
我们要定义一个生产抽象系统的接口,在抽象工厂接口中决定要生产什么型号的电脑以及那种系统。
//定义一个抽象产品接口
interface Computer{
void printComputer();
}
//定义一个具体产品电脑A
class ComputerA implements Computer{
@Override
public void printComputer() {
System.out.println("这是电脑A,4500元");
}
}
//定义一个具体产品电脑B
class ComputerB implements Computer{
@Override
public void printComputer() {
System.out.println("这是电脑B,4000元");
}
}
//定义一个抽象系统接口,生产电脑系统
interface ComputerSystem{
void printSystem();
}
//定义一个os系统
class OsSystem implements ComputerSystem{
@Override
public void printSystem() {
System.out.println("这是os系统");
}
}
//定义一个Windows系统
class WindowsSystem implements ComputerSystem{
@Override
public void printSystem() {
System.out.println("这是Windows系统");
}
}
//定义一个生产电脑和系统的工厂
interface Factory{
Computer createComputer();
ComputerSystem createSystem();
}
//工厂AO 生产电脑A和os系统
class AOFactory implements Factory{
@Override
public Computer createComputer() {
return new ComputerA();
}
@Override
public ComputerSystem createSystem() {
return new OsSystem();
}
}
//工厂BW:生产电脑B和Windows系统
class BwFactory implements Factory{
@Override
public Computer createComputer() {
return new ComputerB();
}
@Override
public ComputerSystem createSystem() {
return new WindowsSystem();
}
}
public class Client{
public static void main(String[] args){
Client client = new Client();
Factory factory = new AOFactory();
//葵葵想要os系统的电脑A
Computer computer = factory.createComputer();
ComputerSystem computerSystem = factory.createSystem();
client.buyComputer(computer);
client.use(computerSystem);
System.out.println("\n");
//她有想要Windows系统的电脑B
Factory factory1 = new BwFactory();
Computer computer1 = factory1.createComputer();
ComputerSystem computerSystem1 = factory1.createSystem();
client.buyComputer(computer1);
client.use(computerSystem1);
}
public void buyComputer(Computer computer){
computer.printComputer();
}
public void use(ComputerSystem computerSystem){
computerSystem.printSystem();
}
}
这样的工厂可以生产多种产品,对于复杂对象的生产易于操作。