你所说的单例(singleton)只能实例化一次,因此它是保持对象存活的好地方,这些对象可以在应用程序生命周期内使用。对于mvc项目,单例对象对于每个请求都是相同的。
在你的第二种方法中,你的SmtpClient不需要每次创建一个新实例并进行处理。
从msdn文档中可以看出:
“SmtpClient”类的实现池化SMTP连接,以便它可以避免为了向同一服务器发送每个消息而重新建立连接的开销。应用程序可以重复使用相同的SmtpClient对象,向同一SMTP服务器和许多不同的SMTP服务器发送许多不同的电子邮件。因此,无法确定应用程序何时完成使用SmtpClient对象并且应该清除它。
因此,它是单例实用程序服务的好候选者。
单例模式将如下所示:
public class SmtpUtilityService : ISmtpUtilityService, IDisposable
{
private readonly SmtpClient _smtpClient;
public SmtpUtilityService()
{
_smtpClient = new SmtpClient([...]);
}
public async Task SendEmail(str eaddress)
{
await _smtpClient.SendAsync([...]);
}
public void Dispose()
{
if(_smtpClient != null)
{
_smtpClient.Dispose();
}
}
}
在您的Statup.cs中,将SmtpUtilityService添加为IServiceCollection的singleton,这样您的SmtpClient将仅被实例化一次。
顺便说一下,Microsoft不建议使用SmtpClient(在某些平台上已过时,在其他平台上也不推荐使用),所以不确定它是否是一个好选择 :/
关于您的第一个方法ConvertMeterToMiles(int mtr),它只是一个转换,每次只需进行一次计算。它不需要任何属性,并且不需要实例。因此,完全静态类是个好选择。
public static class MeterHelper
{
public static decimal ConvertMeterToMiles(int mtr)
{
return mtr * 0.0006213712;
}
}
个人而言,我并不经常使用单例模式。如果我需要属性,我会使用作用域或瞬态服务,如果不需要,则使用完整的静态类(助手)。
SMTPClient
,那么它就有一个依赖关系,但是您不会将其显示给外部世界。相反,它应该通过构造函数注入来获取该对象。当构建容器时,必须决定这两个类中的一个或两个类是否应具有瞬态、作用域或单例生命周期。 - Oliver