莫方教程网

专业程序员编程教程与实战案例分享

探讨ASP.NET Core 中依赖注入的三种方式及适用场景

在 ASP.NET Core 中,理解依赖注入(DI)和如何注册服务是至关重要的。

依赖注入的三种常见注册方式分别是:SingletonTransientScoped

注册方式决定了对象实例的生命周期,以及它们如何在整个应用程序中共享。

一个错误的选择,可能导致内存泄漏、数据混乱、性能下降……

接下来,我们将深入探讨这三种注册方式及适用场景。

Singleton(单例)

定义

Singleton 是一种服务注册方式,它保证在应用程序生命周期内只会创建一个服务实例,并且这个实例会在每次需要该服务时被重用。这意味着无论调用多少次,返回的始终是同一个实例。

适用场景

  • o 对于那些需要跨多个请求共享状态的服务,Singleton 是一个理想的选择。
  • o 它适用于不会发生更改或维护全局状态的服务,比如日志记录、配置管理、缓存等。

代码

public class MySingletonService
{
    public MySingletonService()
    {
        Console.WriteLine("MySingletonService 实例化");
    }

    public string GetMessage() => "我是一个单例服务";
}

services.AddSingleton<MySingletonService>();

每次从容器获取 MySingletonService 时,它都会返回同一个实例

注意事项:

  • o Singleton 会持续存在于整个应用程序生命周期,直到应用程序结束。
  • o 如果 Singleton 服务依赖其他服务,那么这些依赖服务的生命周期必须至少是 Singleton

Transient(瞬态)

定义

Transient 是一种服务注册方式,它每次请求都会创建一个新的实例。这意味着每次从容器获取该服务时都会返回一个全新的对象。

适用场景

  • o 当你需要一个短生命周期的服务,且该服务不持有任何状态时,可以使用 Transient
  • o 适合于轻量级的、无状态的服务,如数据处理或临时的操作服务。

###代码

    services.AddTransient<MyTransientService>(); 

每次从容器获取 MyTransientService 时,它都会创建一个新的实例

注意事项:

  • o Transient 服务的实例会在每次请求时被创建,因此它适合那些不需要持久化状态的服务。
  • o 如果 Transient 服务依赖于其他服务,那么这些依赖服务的生命周期也应该尽量是 Transient

Scoped(作用域)

定义

Scoped 是一种服务注册方式,它的实例会在一个请求或一个作用域(例如,一个用户请求的生命周期)内创建,并且在整个作用域内共享同一个实例。当作用域结束时,实例会被销毁。

适用场景

  • o Scoped 适用于那些在请求期间共享状态的服务,比如数据库上下文等。通常在处理请求时,每个请求需要自己的服务实例,但是这些服务实例在整个请求中保持一致。
  • o 它适用于那些需要在请求生命周期内保持状态,但不应跨请求共享状态的服务。

代码

    services.AddScoped<MyScopedService>();

每个请求都会创建一个新的 MyScopedService 实例,但在同一个请求期间,它会始终保持一致:

注意事项:

  • o Scoped 适合于与每个请求相关的服务,比如数据库连接等。
  • o 如果 Scoped 服务依赖其他服务,那么这些依赖服务的生命周期应该至少是 Scoped

选择

场景推荐生命周期全局缓存、配置读取Singleton每次调用都要独立计算或验证Transient数据库操作、请求上下文信息Scoped服务依赖其他 Scoped/TransientScoped服务依赖 Singleton可用任何服务被 Scoped 使用建议 Scoped 或 Transient

比较

生命周期注册方式服务实例化频率适用场景单例(Singleton)AddSingleton<T>()应用程序生命周期内唯一实例跨请求共享状态的服务瞬态(Transient)AddTransient<T>()每次请求都创建新的实例短生命周期、无状态的服务作用域(Scoped)AddScoped<T>()每个请求一个实例请求级别的状态共享服务

控制面板
您好,欢迎到访网站!
  查看权限
网站分类
最新留言