VContainer-resolving/constructor-injection | 解析——构造函数注入

通常情况下,依赖项在首次解析时会被构造并注入(有一些例外 情况)。

当注册一个需要依赖项的类时,提供一个构造函数并将依赖项作为参数传入。VContainer 会处理剩下的工作。

:::note
目前支持构造函数中的可选参数。如果构造函数依赖项缺失,VContainer 在构建或验证容器时会抛出异常。
:::

基本示例:

class ClassA
{
    readonly IServiceA serviceA;
    readonly IServiceB serviceB;
    readonly SomeUnityComponent component;

    public ClassA(
        IServiceA serviceA,
        IServiceB serviceB,
        SomeUnityComponent component)
    {
        this.serviceA = serviceA;
        this.serviceB = serviceB;
        this.component = component;
    }
}

上面的代码示例没有使用 VContainer 的 API,因为它不需要。如果愿意,仍然可以手动使用相同的构造函数创建 ClassA 的实例。

:::caution
Unity 会从构建中移除未使用的代码,当涉及反射或 IL 代码生成时(VContainer 就是这种情况)经常会出错。为了防止误删构造函数,使用 link.xml 文件或在一个构造函数上添加 [Inject] 属性。这同样适用于方法注入
:::

    [Inject]
    public ClassA(
        IServiceA serviceA,
        IServiceB serviceB,
        SomeUnityComponent component)
    {
        // ...
    }

:::note
如果一个类有多个构造函数,除非恰好一个构造函数定义了 [Inject],否则 VContainer 会抛出异常。在这种情况下,VContainer 在解析依赖项时会优先使用该构造函数。
:::

:::tip 推荐
尽可能使用构造函数和 readonly 字段进行注入。原因如下:

  • 这是最简单的注入形式。
  • 如果与 VContainer 一起使用,类可以安全地假设其依赖项已被解析(否则它不会被构造)。
  • 类中没有魔法;甚至可以在不使用 VContainer 的情况下进行实例化(例如用于测试)。
  • 类的依赖关系变得显而易见。当类承担了太多职责时,也很容易看出来(因为它的构造函数会变得太大)。
    :::

MonoBehaviour

MonoBehaviours 不支持构造函数。请使用方法注入属性/字段注入 代替。

抑制警告

Unity 包含 一组由 JetBrains 定义的代码分析属性,一些 IDE(包括 Rider)使用这些属性进行代码分析。如果 IDE 将注入构造函数标记为未使用,请应用 [UsedImplicitly](可能带有 ImplicitUseKindFlags.InstantiatedNoFixedConstructorSignature):

public class Dependency
{
    [UsedImplicitly(ImplicitUseKindFlags.InstantiatedNoFixedConstructorSignature)]
    public Dependency(GameContext game, StatusContext status)
    {
        _game = game;
    }
}
// 这个类和构造函数不会被标记为未使用,但 status 参数会被标记为未使用。

当构造函数或方法被如此注解时,Rider 会阻止构造函数(和类)被标记为未使用。然而,该构造函数中未使用的参数仍会被标记为未使用。

其他 IDE 的结果可能会有所不同。

posted @   凌雪寒  阅读(12)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· 被坑几百块钱后,我竟然真的恢复了删除的微信聊天记录!
· 没有Manus邀请码?试试免邀请码的MGX或者开源的OpenManus吧
· 【自荐】一款简洁、开源的在线白板工具 Drawnix
· 园子的第一款AI主题卫衣上架——"HELLO! HOW CAN I ASSIST YOU TODAY
· Docker 太简单,K8s 太复杂?w7panel 让容器管理更轻松!
点击右上角即可分享
微信分享提示