目录
前言
对于产品种类相对较少的情况,考虑使用简单工厂模式。使用简单工厂模式的客户端需要传入工厂类的参数,不需要关系如何创建对象的逻辑,可以很方便地创建所需产品。下面我们来使用简单工厂模式创建一个农场管理系统
一、简单工厂模式
简单工厂模式中创建实例的方法通常为静态方法,因此简单工厂模式(Simple Factory Pattern)又叫作静态工厂方法模式(Static Factory Method Pattern)。
简单工厂模式的主要角色如下:
- 简单工厂:简单工厂模式的核心,负责实现创建所有实例的内部逻辑。工厂类的创建产品类的方法可以被外界直接调用,创建所需的产品对象。
- 抽象产品:简单工厂创建的所有产品的父类,负责描述所有实例共有的公共接口。
- 具体产品:由简单工厂进行创建的具体类。
二、农场系统创建
1.先新建一个包、类以及抽象类
package : com.simokeFactory.fruit;
抽象产品角色 | 抽象类 | Fruit |
实现产品角色 | 普通类 | Apple |
实现产品角色 | 普通类 | Grape |
实现产品角色 | 普通类 | Strawberry |
工厂角色 | 普通类 | FruitGardener |
输入异常处理 | 普通类 | Bad FruitException |
客户端 | 普通类 | Client |
2.键入各类中代码
1抽象产品角色 Fruit
package com.simpleFactory.fruit; public interface Fruit { /*****生长*****/ void grow(); /*****收获*****/ void harvest(); /*****种植*****/ void plant(); }
2实现产品角色 Apple
package com.simpleFactory.fruit; public class Apple implements Fruit { private int treeAge; @Override public void grow() { log("苹果正在生长中,请耐心等待..."); } @Override public void harvest() { log("苹果已到收获季,请收获..."); } @Override public void plant() { log("苹果可以种植,请悉心照料..."); } private static void log(String msg) { System.out.println(msg); } public int getTreeAge() { return treeAge; } public void setTreeAge(int treeAge) { this.treeAge = treeAge; } }
3实现产品角色 Grape
package com.simpleFactory.fruit; import java.awt.*; public class Grape implements Fruit{ boolean seedless; @Override public void grow() { Display("葡萄正在生长中,请等待......"); } @Override public void harvest() { Display("葡萄已到收获季,请收获......"); } @Override public void plant() { Display("葡萄可以种植,请悉心照料......"); } private static void Display(String msg) { System.out.println(msg); } public boolean getSeedless() { return seedless; } public void setSeedless(boolean seedless) { this.seedless = seedless; } }
4实现产品角色 Strawberry (后面的步骤和前面一致 我就不一一截图了)
package com.simpleFactory.fruit; public class Strawberry implements Fruit{ @Override public void grow() { Display("草莓正在生长中,请等待......"); } @Override public void harvest(){ Display("草莓已到收获季,请收获......"); } @Override public void plant(){ Display("草莓可以种植,请悉心照料....."); } private static void Display(String msg){ System.out.println(msg); } }
5工厂角色 FruitGardener
package com.simpleFactory.fruit; import com.sun.javaws.exceptions.BadFieldException; public class FruitGardener { public static Fruit factory(String fruit) throws BadFruitException{ if(fruit.equalsIgnoreCase("apple")) return new Apple(); else if(fruit.equalsIgnoreCase("strawberry")) return new Strawberry(); else if(fruit.equalsIgnoreCase("grape")) return new Grape(); else throw new BadFruitException("Bad fruit request"); } public static void factory(String fruit,String farmwork) throws BadFieldException, BadFruitException { if(farmwork.equalsIgnoreCase("grow")) { FruitGardener.factory(fruit).grow(); } else if(farmwork.equalsIgnoreCase("harvest")) { FruitGardener.factory(fruit).harvest(); } else if(farmwork.equalsIgnoreCase("plant")) { FruitGardener.factory(fruit).plant(); }else if(farmwork.equalsIgnoreCase("strawberry")) { FruitGardener.factory(fruit).plant(); }else if(farmwork.equalsIgnoreCase("grape")) { FruitGardener.factory(fruit).plant(); } else throw new BadFruitException("Bad fruit request"); } }
6输入异常处理 Bad FruitException
package com.simpleFactory.fruit; public class BadFruitException extends Exception { public BadFruitException(String msg) { super(msg); } }
7客户端 Client
package com.simpleFactory.fruit; import com.sun.javaws.exceptions.BadFieldException; import java.util.Scanner; public class Client { public static void main(String[] args) { Scanner scanner = new Scanner(System.in); while (true) { String msg1 = null; String msg2 = null; String msg3 = null; System.out.println("请输入水果和状态:"); msg1 = scanner.next(); msg2 = scanner.next(); try { FruitGardener.factory(msg1, msg2); } catch (BadFruitException | BadFieldException e) { System.out.println("很抱歉,您的输入有误,请检查。"); } System.out.println("是否继续?(Y/N)"); msg3 = scanner.next().substring(0); if (msg3.equalsIgnoreCase("N")) System.exit(0); } } }
三、在主方法运行
完成!
总结
扩展一下
@Override这个标签有什么用呢?
1. 可以给你当作注释用,感觉这个也不能说明什么,注释也没什么用。
2. 可以告诉读你代码的人,这是对它父类方法的重写,其实很多代码规范没有为什么,规范就是规范,代码的可读性还是很重要的。
3. 编译器可以给你验证@Override下面的方法名称是否是你父类中所有的,如果没有就会报错。