在 ASP.NET 中,依赖注入 (Dependency Injection, DI) 提供了三种常见的服务生命周期模式:Singleton、Transient 和 Scoped。这些模式决定了服务的实例何时被创建、何时被销毁以及它们在应用程序中的生命周期。
services.AddSingleton<IMyService, MyService>();
services.AddTransient<IMyService, MyService>();
在配置服务时,你可以根据需要选择适当的生命周期模式,确保服务的创建和销毁方式符合应用程序的需求。
Singleton作用域是最容易理解的:进程全局唯一实例。对于Transient和Scope作用域就没有Singleton作用域那么容易理解了。下面通过例子详细说明他们的区别。
对于需要在请求期间保留状态的服务,使用 Scoped 是一个常见选择。如何理解这句话?
我们将创建一个服务,该服务在每个请求期间保留一个状态,并通过 Transient
和 Scoped
生命周期模式来比较它们的行为。
假设有一个简单的计数服务 CounterService
:
public class CounterService
{
private int count = 0;
public int Increment()
{
return ++count;
}
}
现在,我们将在 ASP.NET Core 中注册这个服务,并测试 Transient
和 Scoped
生命周期模式的行为。
Startup.cs
// Startup.cs
public void ConfigureServices(IServiceCollection services)
{
services.AddTransient<CounterService>();
// 其他配置...
}
HomeController.cs
// HomeController.cs
public class HomeController : Controller
{
private readonly CounterService transientCounter;
public HomeController(CounterService transientCounter)
{
this.transientCounter = transientCounter;
}
public IActionResult Index()
{
ViewBag.TransientCount1 = transientCounter.Increment();
ViewBag.TransientCount2 = transientCounter.Increment();
return View();
}
}
在上述代码中,CounterService
被注册为 Transient
生命周期。每次对 CounterService
的请求都会创建一个新的实例。当我们在同一个请求中调用两次 Increment
方法时,count
变量会每次重新初始化。
Startup.cs
// Startup.cs
public void ConfigureServices(IServiceCollection services)
{
services.AddScoped<CounterService>();
// 其他配置...
}
HomeController.cs
// HomeController.cs
public class HomeController : Controller
{
private readonly CounterService scopedCounter1;
private readonly CounterService scopedCounter2;
public HomeController(CounterService scopedCounter1, CounterService scopedCounter2)
{
this.scopedCounter1 = scopedCounter1;
this.scopedCounter2 = scopedCounter2;
}
public IActionResult Index()
{
ViewBag.ScopedCount1 = scopedCounter1.Increment();
ViewBag.ScopedCount2 = scopedCounter2.Increment();
return View();
}
}
在上述代码中,CounterService 被注册为 Scoped 生命周期。在同一个请求中,CounterService 的实例是共享的。当我们在同一个请求中调用两次 Increment 方法时,count 变量在整个请求期间保留其状态。
总的来说,Transient 生命周期每次都创建一个新的实例,适合不需要保留状态的服务。而 Scoped 生命周期在同一个请求期间共享一个实例,适合需要在请求期间保留状态的服务。
原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。
如有侵权,请联系 cloudcommunity@tencent.com 删除。
原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。
如有侵权,请联系 cloudcommunity@tencent.com 删除。