2010-10-21 126 views
4

我有一个c#web服务。当我得到一个新的请求时,我创建一个日志记录实例。我有很多其他类的实例来处理请求,我也希望它们能够记录。共享日志记录实例而不将其传递给构造函数或属性的最佳方式是什么?如何与多个类共享一个类的实例?

+0

你正在使用什么日志框架? – 2010-10-21 23:59:07

+2

下面的答案很好(基本上使用一个静态实例,由单身守卫)。不过,可以考虑使用DI容器来管理它。使每个人的生活更轻松。 – RPM1984 2010-10-22 00:06:47

回答

3

Singleton Pattern is an anti-pattern;我无法想象应该使用或推荐使用或推荐的很多情况,包括在这种情况下,用于日志记录。

我们如何处理日志记录:通过构造器注入将日志记录实例注入到所有需要它的类中。例如:

public class MyClass 
{ 
    private readonly ILogger _logger; 

    public MyClass(ILogger logger) 
    { 
     _logger = logger; 
    } 

    public void DoStuff() 
    { 
     _logger.Trace("DoStuff called"); 
    } 
} 

测井例如注射,每次可以是一个新的实例,或者如果你是在具有可创建一次,并通过根据需要在单个实例记录器弯曲。

但是,我强烈建议第一个选项,使用DI来构建您的类使用Composition Root模式。我还建议使用日志框架,例如NLog或log4net。这些可配置并易于使用的电子邮件,事件查看器,文件等。在多线程环境中工作。

我们有自己定义的ILogger,它有Trace,Warn,Info,Exception等等,然后用NLog实现这个接口。这意味着我们可以通过创建ILogger的新实现并进行简单的DI配置更新来轻松更改我们的日志记录。这是迄今为止我们工作得很好的一种日志记录解决方案。

+0

这是一种劣质的方法 - 尤其是如果你有几个类似的要求,你的构造者看起来很荒谬。它远远优于让你的班级具有智慧并且能够自主决定他们的环境。整个DI理论是业余的,马虎的。静态类没有什么问题,如果你正在编写c#,那么当你引用任何MS核心程序集时,你已经完全绑定了它们。 String.Format() - 等...不妨使用Logging.Log() – hajikelist 2015-05-11 16:27:11

0

那么,你可以让你的日志记录类包含静态方法,这些方法将实际写入内存/刷新到磁盘。你也可以看看Singleton Pattern

-1

使用一个静态字段(我假设C#支持这些)。语法应该与此类似:

private static final Logger logger = new Logger(...); 

并且只要您需要在课程中记录某些内容时使用它。

+0

我认为你的意思是只读而不是最后? – 2010-10-22 00:00:21

+0

我是Java开发人员。这对我们来说是'最后的'。 ;-)。是的,那是我的最终答案.... – 2010-10-22 00:23:49

0

您可以使用Singleton Pattern确保整个系统中只有一个记录对象实例。

将日志对象传递给构造函数或属性实际上会使您的代码更易于测试,具体取决于您如何实现Singleton模式。日志记录是那些令人烦恼的交叉问题之一,总是有权衡。

0

通常在每个班级中创建记录器的新实例并不是问题。 Log4Net记录器构造函数采用一种类型作为参数,为您提供更好的日志。

3

通常某种静态类/属性的用于共享的对象,而无需到处通过引用,例如:

public class Logger 
{ 
    static Logger() 
    { 
     this.Instance - new Logger(); 
    } 

    public static Logger Instance 
    { 
     get; 
     private set; 
    } 

    // Other non-static members 
} 

用法:

Logger.Instance.Log(); 

通常这种(或至少在此变化)被称为singleton pattern

上有上述许多变化,例如下列细微变化是比在日志框架上述多见:

public class Logger 
{ 
    static Logger() 
    { 
     this.Instance = new Logger(); 
    } 

    public static Logger Instance 
    { 
     get; 
     private set; 
    } 

    public static void Log() 
    { 
     Logger.Instance.Log(); 
    } 
} 

用法:

Logger.Log(); 
+0

这是一个最佳解决方案;把Logger放在自己的库中,这样你就可以从其他项目中引用它。 – 2010-10-22 00:38:21

2

Singleton模式。

也就是说,一个具有私有构造函数的类。您使用公共静态方法仅创建该类的一个实例并返回该对象。

编辑:另外值得注意的是,您需要将此类放在其自己的项目中,以便它可以被所有类引用。

相关问题