6
class Bus<T>
{
    static Bus()
    {
        foreach(FieldInfo fi in typeof(T).GetFields())
        {
            if(fi.FieldType == typeof(Argument))
            {
                fi.SetValue(typeof(T), new Argument("busyname", "busyvalue"));
            }
        }
    }
}
class Buss : Bus<Buss>
{
    public static Argument field;
}

Any ideas how to make this work so that a reference to the static field in Buss triggers the static constructor in Bus?

2
  • 1
    why static contructors? A static constructor is used to initialize any static data, or to perform a particular action that needs to be performed once only. Commented Jun 17, 2011 at 19:48
  • 1
    'field' is static data and only needs to be initialized once, hence static constructors. Commented Jun 17, 2011 at 20:06

3 Answers 3

3

The fact that this matters to you probably means that you are using static constructors wrong.

With that in mind, you could make a static constructor in Buss that manually invokes the static constructor in Bus. Note that it's not possible to run a static constructor more than once.

Sign up to request clarification or add additional context in comments.

5 Comments

static constructor cannot be called directly.
I realize by 'wrong' that you probably mean my OOP is off. However, I feel that to be able to inherit static members (including static constructors) would actually be more object-oriented.
@adt: Just refer to any static field or method, and it will be called implicitly.
can you directly call static contructor?
@adt: Not explicitly, but calling it can be accomplished, like I mentioned.
2

The static constructor of a generic type is invoked exactly once per Type, when that type is referenced.

Calling Buss x = new Buss() will invoke the static constructor of Bus<Buss>.

Calling Bus<Buss> x = new Bus<Buss>() will also invoke the static constructor of Bus<Buss>, but it will do so for it's type argument Buss, setting Buss.field.

If you create a class Bugs : Bus<Buss> it will never set Bugs.field, as it will first resolve the type argument Buss, which invokes the static constructor of it's base class Bus<Buss>, setting Buss.field. When it tries to call the static constructor of Bugs base class, it will think it had already invoked the static Bus<Buss> constructor and skip it.

Basically if I copy paste your code, create a dummy Argument class and create a new instance of Buss, the static constructor is invoked and Buss.field is set to an instance of Argument, but I do recognize some strange behavoir here in which I'd have to advise not to use reflection from a static method to reach subclasses' statics.

The example you provided only works because Buss is the type argument for itself.

Comments

1

MSDN says that 'Static constructors are not inherited'. I guess this is similar to static fields which are not inherited either.

1 Comment

"static fields which are not inherited": I have in my code (boiled down) class T1{ public static string s1="s1"; } class T2: T1 { void f(){ Console.WriteLine(s1); }}. Does that not count as inheritance? One could legitimately expect that the static constructor of a base class is executed before the static constructor of one of its subcclasses is executed, since it may perform static initializations needed by the derived class as well.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.