SlowCoder74
SlowCoder74

Reputation: 93

C# Can/should a List<> of a class be a static member of the same class?

My example:

class MyClass
{
    public int a = 1;

    public static List<MyClass> list = new List<MyClass>();
}

class Program
{
    static void Main(string[] args)
    {
        MyClass.list.Add(new MyClass() { a = 5 });
        MyClass.list.Add(new MyClass() { a = 10 });
        foreach (MyClass item in MyClass.list) Console.WriteLine(item.a);

        Console.ReadKey();
    }

This code works, and shows that my list, which is statically defined within the MyClass class itself, is populating as I'd expect.

Is there any reason not to define my list in this manner?

Upvotes: 2

Views: 2707

Answers (2)

willeM_ Van Onsem
willeM_ Van Onsem

Reputation: 476534

Actually this code shows a lot of sign of (very) bad desing.

First of all one better doesn't make fields public. All other classes/object can now alter the value of that variable in objects. Perhaps you don't see much problems with that, but imagine that at one point in time you want to restrict the range of values that variable can have, or that it depends on the value of another field. Properties (with getters and setters) and methods are used to shield an field from external usage, they need to guarantee that the object always remains in a valid state.

Next about the list, again don't make such lists public - unless you are confident that there is no problem -. But furthermore using statics is by some researchers considered to be bad design as well. The list maintains a state, but since it is static, this is a global state. Global states are problematic since they don't allow (easy) unit testing, and can become problematic if for some reason the list should be not that global.

In case you really want to make some access point for data, you can perhaps consider making a class that stores such list and pass it around in your program.


There are a few exceptions, for instance the Flyweight pattern where one indeed maintains a global state. Those examples are merely used to increase performance. For instance:

public class FlyWeightInstance {

    private int value; //<- private field
    private static Dictionary<int,FlyWeightInstance> dic = new Dictionary<int,FlyWeightInstance>(); //<- private static cache

    private int FlyWeightInstance (int value) { // <-- private constructor
        this.value = value;
    }

    public static FlyWeightInstance (int value) {
        FlyWeightInstance res;
        if(!dic.TryGetValue(value,out res)) {
            res = new FlyWeightInstance(value);
            dic.Add(value,res);
        }
        return res;
    }

}

Upvotes: 2

Mark Shevchenko
Mark Shevchenko

Reputation: 8197

Such a solution is used sometime, f.e. to implement the Singleton or Register-Resolve patterns.

But you should keep in mind that it's not well suited for multithread environment. Typically, a static collection should be private, and access methods (including property getter and setter) should be synchronized.

In additional, static fields/properties are difficult to an unit testing.

Upvotes: 4

Related Questions