静态属性-如何正确初始化它?

时间:2018-09-27 15:21:55

标签: c# static

我正在重构一些代码。我的项目中有很多使用相同数据的报告。例如,他们每个人都使用List<Product>,它是通过数据库检索的。

到目前为止,我有重复的行,例如:

var products = MyDatabase.Products.ToList(); 

我想要一个带有静态属性的静态类,供我的报告使用。

我想在报告中添加最后一行,例如:

var products = MyStaticClass.Products; 

我想一次加载此列表,并允许我的报告使用它,而不是每次不同的报告想要该列表时都引用数据库。

我已经读过这个,解决方案似乎是:

1)

public static List<Product> Products 
{
    get
    {
        return MyDatabase.Products.ToList(); 
    }
}

2)

public static List<Product> Products { get; set;} = MyDatabase.Products.ToList();

3)

public static List<Product> Products = MyDatabase.Products.ToList();

4)

private static  List<Product> _products;

public static List<Product> Products
{
    get 
    { 
        return _products ?? 
            ( _products = MyDatabase.Products.ToList()); 
    }
}

5。

private static Lazy<List<Product>> _products =
    new Lazy<List<Product>>(() => MyDatabase.Products.ToList());

public static List<Product> Products
{
    get { return _products.Value; }
}

据我了解,第一种情况在我每次访问MyDatabase.Products.ToList()时都会调用,因此这不是您想要的行为。

第二个选项几乎与第一个类似。有什么区别吗?或者只是第一个的较新版本。

第三个选项意味着只调用一次MyDatabase.Products.ToList(),但是它将始终被调用,而与实际用法无关。关闭,我想。

第4个或第5个选项是否优于上述选项? Lazy<T>是我的最佳选择吗?它只会在被调用时(如果被调用)加载数据吗?

请说明我是否正确理解了这些选项,并为我提供了理想的解决方案。

1 个答案:

答案 0 :(得分:2)

这是您做过的最糟糕的决定:C#是一种面向对象的编程,即使在其他范例中,它也听起来像是一种设计气味。

因此,您想在许多报告中共享一些数据:依赖注入怎么样?设计您的类,以便能够注入共享数据:

public class Report 
{
     public Report(List<Product> products /* other arguments */) 
     {
           Products = products;
     }

     private List<Product> Products { get; }
}

全局状态不是一个好主意,因为...

许多人可以访问,修改它。现在,在方程式中添加一些线程/并行性,您将需要额外的精力和复杂性来同步全局状态的读/写操作。

此外,这也是内存泄漏的一种证明:这些引用在整个应用程序生命周期中都是有效的。

避免全局状态:接受依赖项注入。