Supplier本身就是最轻量级的函数式工厂接口,仅含get()方法实现按需提供对象,天然支持惰性创建、无状态对象生成及高阶组合,无需额外工厂类包装。

Supplier 本身就是一个“惰性创建”的天然载体,它不依赖工厂模式也能实现对象的延迟初始化;所谓“通过工厂模式实现”,其实是把 Supplier 当作工厂的简化抽象——它本身就是最轻量级的工厂接口。
Supplier 就是函数式工厂接口
Java 的 SupplierMyServiceFactory.create())的目标完全一致,只是更简洁、更通用、更易组合。
不需要额外设计“工厂类”来包装 Supplier,直接用它就是工厂:
- 它无参数、无依赖,天然适合创建无状态或配置驱动的对象
- 每次调用
get()都可生成新实例(或返回缓存实例,取决于实现) - 可被传入方法、存储在集合、延迟执行,完美支持惰性语义
常见惰性创建场景与写法
以下都是 Supplier 实现“延迟构造”的典型方式,无需额外工厂类:
立即学习“Java免费学习笔记(深入)”;
-
延迟创建昂贵对象:
Supplier<connection> connSupplier = () -> DriverManager.getConnection(url);</connection>真正用时才连数据库,避免启动时阻塞或失败 -
配合 Optional 或 Stream 做条件创建:
Optional.ofNullable(config).map(c -> (Supplier<list>>) () -> loadList(c)).orElse(() -> Collections.emptyList).get();</list> -
带内部缓存的惰性单例(非线程安全版):
Supplier<mapper> cachedMapper = new Supplier() { private Mapper instance; public Mapper get() { return instance == null ? instance = new MyMapper() : instance; } };</mapper>(更推荐用LazyVal模式或AtomicReference,但 Supplier 可承载该逻辑)
如果非要结合传统工厂类,Supplier 是它的适配器
当已有老式工厂类(如 ReportFactory),可用 Supplier 包装它,使其融入函数式流:
Supplier<report> reportSupplier = () -> ReportFactory.create("daily");</report>- 然后用于日志、重试、超时等高阶操作:
retryUntilSuccess(3, reportSupplier)—— 重试时每次都重新调用get(),即新建 Report
此时 Supplier 不是“被工厂模式实现”,而是“让工厂能力函数式化”,提升复用性和表达力。
注意:Supplier 本身不管理生命周期
它只承诺“调用时给一个对象”,不保证是新实例、单例还是共享对象。是否惰性、是否缓存、是否线程安全,全由具体实现决定:
- `() -> new ExpensiveService()` → 每次都新建(真惰性)
- `new MemoizedSupplier(() -> initHeavyResource())` → 首次调用初始化,后续返回缓存(伪惰性+单例)
- 用
ThreadLocal.withInitial(...)返回 Supplier → 每线程惰性初始化
这些变体都不需要改变 Supplier 接口,只需替换其实现策略。


















