You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

工厂构造函数中智能指针的设计困境及解决方案咨询

工厂模式下的依赖生命周期管理问题

问题场景

当前使用工厂在运行时根据用户选择创建对象,代码如下:

class UpdateServiceFactory{
  public:
    std::unique_ptr<UpdateService> create(Widget widget){
       if(widget.name == "name one"){
          auto dependency = std::make_unique<ChildDependency>();
          return std::make_unique<ChildUpdateService>(std::move(dependency));
       }
  }
}

ChildUpdateService的构造有两种选择:

  • a) 接收std::unique_ptr<ChildDependency>:能实现UpdateService销毁时依赖自动释放,但强制创建者遵循单所有权策略,同一依赖无法复用给其他类;
  • b) 接收原始指针:可通过unique_ptr::get()传递,但存在生命周期管理风险,工厂若承担生命周期管理则违反单一职责原则(SRP)。

咨询以下两个问题:

  1. 构造函数接收unique_ptr是否不合理地强制了创建者的生命周期策略?
  2. 是否有合适的设计模式解决该问题,比如用中间对象管理dependency的生命周期?

问题解答

1) 关于unique_ptr强制生命周期策略的合理性

构造函数接收unique_ptr确实会强制创建者遵循单所有权的生命周期策略。这种设计在依赖明确属于被创建服务独占的场景下是合理的,但如果存在依赖复用的需求,这种强制就会变成不必要的限制——因为unique_ptr的移动语义要求所有权完全转移,创建者在传递后就失去了对该依赖的控制权,无法再将其复用给其他对象。所以如果你的场景中存在依赖复用的可能,这种设计就是不合理的。

2) 可行的解决方案

针对这个问题,有几种符合设计原则的解决思路:

  • 使用std::shared_ptr管理依赖:将依赖的所有权改为共享模式,ChildUpdateService的构造函数接收std::shared_ptr<ChildDependency>。工厂创建依赖时用std::make_shared,传递给服务时无需移动,多个服务可以共享同一个依赖实例,生命周期由引用计数自动管理。这种方式既不用工厂额外承担生命周期管理,也解决了依赖复用的问题。
  • 引入依赖注入(DI)容器:专门的DI容器负责所有依赖的生命周期管理(比如单例、请求作用域等),工厂只需要从容器中获取已创建的依赖实例,再组装成目标服务。这种方式严格遵循SRP——工厂仅负责对象的创建组装,容器负责依赖的生命周期,同时能灵活配置依赖的复用策略。
  • 独立的生命周期管理器:创建一个DependencyManager类,专门负责依赖的创建、存储和销毁。工厂从管理器中获取依赖的引用(或shared_ptr)来创建服务,完全不涉及生命周期管理逻辑,符合单一职责原则。管理器可以根据需求配置依赖的复用规则(比如单例、临时实例等)。

内容的提问来源于stack exchange,提问作者gfree

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.19 10:50:23