Dear all, the question like this one has been already asked, but among the answers there was no explanation of the problem which I see.
The problem: the C# Programming Guide says:
A static constructor is used to initialize any static data, or to perform a particular action that needs performed once only. It is called automatically before the first instance is created or any static members are referenced.
In particular, static constructor is called before any instance of a class is created. (This doesn't ensure that the static constructor finishes before creation of instance, but this is a different story.)
Let's consider the example code:
using System;
public class Test
{
static public Test test = new Test();
static Test()
{
Console.WriteLine("static Test()");
}
public Test()
{
Console.WriteLine("new Test()");
}
}
public class Program
{
public static void Main()
{
Console.WriteLine("Main() started");
Console.WriteLine("Test.test = " + Test.test);
Console.WriteLine("Main() finished");
}
}
It outputs:
Main() started
new Test()
static Test()
Test.test = Test
Main() finished
So we can see that the instance constructor finishes (and thus an instance is created) before the static constructor starts. Doesn't this contradict the Guide? Maybe the initialization of static fields is considered to be an implicit part of static constructor?
Inline initializers for static fields run before the explicit static constructor.
The compiler transforms your class into something like this:
public class Test {
.cctor { //Class constructor
Test.test = new Test(); //Inline field initializer
Console.WriteLine("static Test()"); //Explicit static ctor
}
.ctor { ... } //Instance constructor
}
Note that this is independent of the declaration order.
To quote the spec:
The static field variable initializers
of a class correspond to a sequence of
assignments that are executed in the
textual order in which they appear in
the class declaration. If a static
constructor (Section 10.11) exists in
the class, execution of the static
field initializers occurs immediately
prior to executing that static
constructor.
Related
I am wondering why my static constructor is outputting default constructor Static Constructor, and not the other way around Static Constructor and Default constructor or just Default constructor. When I use a static constructor, it should execute the static constructor first. However, from the code below,
The First question: why is the default constructor is called before the static constructor?
class Program
{
static void Main(string[] args)
{
var test = Single.S;
}
class Single{
static readonly Single s = new Single();
public static Single S{
get { return s; }
}
private Single(){
Console.WriteLine("Default");
}
static Single(){
Console.WriteLine("staic");
}
}
}
The Second question: How come the Static Single constructor is being called as well?
Depending on Microsoft
A static constructor is used to initialize any static data, or to
perform a particular action that needs to be performed once only. It
is called automatically before the first instance is created or any
static members are referenced.
class SimpleClass
{
// Static variable that must be initialized at run time.
static readonly long baseline;
// Static constructor is called at most one time, before any
// instance constructor is invoked or member is accessed.
static SimpleClass()
{
baseline = DateTime.Now.Ticks;
}
}
In this case, the static constructor will be called before the default constructor
but in this line,
static readonly Single s = new Single();
you are using "static field initialization"
The static field variable initializers of a class correspond to a sequence of assignments that are executed in the textual order in which they appear in the class declaration. If a static constructor exists in the class, execution of the static field initializers occurs immediately prior to executing that static constructor.
in this case, static field initialization will be completed before the constructor is called,
then the static constructor is run before your default constructor,
but when it runs, it's using new Single(), so passing through your non-static constructor path.
This causes to call the default constructor before the static constructor.
Finally, you can try this and you will see it will execute
the static constructor before the default constructor
private class Single
{
private static readonly Single s;
static Single()
{
Console.WriteLine("static");
s = new Single();
}
}
References
C# and beforefieldinit
When is a static constructor called in C#?
How does static field initialization work in C#?
Static constructor called after instance constructor?
Static constructor can run after the non-static constructor. Is this a compiler bug?
The first thing that happens here when loading the class is
static Single s = new Single();
C# executes static initializers like this in the order they are seen. I am not sure if this ordering point also applies to the static constructor but from your test it seems that the static initializer does occur before the static constructor.
In any case, in order to assign to static Single s, one must first construct new Single(), which means invoking the non-static constructor. I am not sure what you would get if you read from Single.s in the non-static constructor but I would expect either null or an exception.
My friend told me that the following is one of the ways to create singleton design pattern in C#
public class class1{
public static class1 Obj { get; private set; }
static class1()
{
Obj = new class1();
}
}
He told me that the static constructor runs only one time in application, so only one instance of class1 will be created,
but I see that I have to add this if(Obj==null) to check the existence of object
public class class1{
public static class1 Obj { get; private set; }
static class1()
{
**if(Obj==null)**
Obj = new class1();
}
}
which code is correct?
Assuming that the only place where Obj is set is in the static constructor, the first code snippet is correct; the second code snippet is redundant.
Since static constructors run only once per class. If there is no other path to set Obj, its value will always be null at the beginning of the static constructor. Therefore, the check if(Obj==null) will always succeed, which makes it redundant.
The static constructor will only ever be called once, at some point prior to the static variables being allocated.
Which means that your friend is correct, you do not need the if statement - it is redundant.
This is because you cannot call a static constructor manually, it will only be called once, at the start of run-time.
Further reading : https://stackoverflow.com/a/4506997/617485
This is a simple program I created - one table class, one main class. In the table class I created a print method which simply outputs my name. From the main class I am calling the print method but not getting the output.
namespace ConsoleApplication3
{
class table
{
public static void print()
{
Console.WriteLine("My name is prithvi-raj chouhan");
}
}
class Program
{
public static void Main()
{
table t = new table();
t.print(); // Error the program is not giving output while calling the print method
}
}
}
Since the function you are calling is static.
Use this syntax
public static void Main()
{
table.print();
}
Quote from MSDN:-
A static method, field, property, or event is callable on a class even
when no instance of the class has been created. If any instances of
the class are created, they cannot be used to access the static
member. Only one copy of static fields and events exists, and static
methods and properties can only access static fields and static
events. Static members are often used to represent data or
calculations that do not change in response to object state; for
instance, a math library might contain static methods for calculating
sine and cosine.
print is a static method, so call it as a static method:
public static void Main()
{
table.print();
}
try this:
class Program
{
public static void Main()
{
table.Print();
}
}
Print(); is a static method so you dont need to instantiate a new Table object in order to access it's methods
You are calling print() as an instance method but it is static. Try to remove the static keyword from the method.
Try to add a Console.ReadLine(); after table.print();.
UPDATE:
Missed the part with static, now corrected.
I have a job interview tomorrow and I'm trying to answer this question:
There is a class named C and method m in this class, this class have also empty constructor:
Main ()
{
C c = new c();
}
Class C {
public c {
//empty constructor
}
public m {
//does something - doesnt mind
}
}
And what you have to do is to change the code so that in a creation of an instance class C, the method m would be called before the class constructor.
You have to do this without changing the main (edit only the class code).
Thanks in advance!
Like the other answers have said, you can make the method static. But then you need to explicitly call it. If you make a static class constructor, that will get called once automatically (you don't need to call it), the first time the class is referenced (like when you construct the first instance). You can't exactly control when it executes, but it will execute before the first instance is constructed. Based on the way they've worded the question (you can't change the Main method), I think static class constructor is the answer they're looking for.
http://msdn.microsoft.com/en-us/library/k9x6w0hc%28v=vs.80%29.aspx
Static constructors have the following properties:
A static constructor does not take access modifiers or have parameters.
A static constructor is called automatically to initialize the class before the first instance is created or any static members are
referenced.
A static constructor cannot be called directly.
The user has no control on when the static constructor is executed in the program.
Java doesn't have static class constructors, but they do have static initialization blocks..
static {
// code in here
}
To call a class's method before its constructor gets called you either have to turn this method into static so you don't need an instance of that class to call it, or (in C#) you can use FormatterServices.GetUninitializedObject Method to get an instance of your class without running the constructor (which of course may not be a wise thing to do).
In JAVA:
make method static and call your method in static block.
class C{
static{
m();
}
public C() {
System.out.println("Constructor Called..");
}
public static void m() {
System.out.println("m() is called.");
}
}
Main call
public static void main(String[] args) {
new C();
}
In both Java and C# you can use, base class constructors, static constructors (Edit: static initializer block in Java), and field initializers, to call code before the C class's constructor executes without modifying Main.
An example using a field initializer block in Java:
class C {
{ m(); }
public C() {
System.out.println("cons");
}
public void m() {
System.out.println("m");
}
}
This prints "m", then "cons". Note that m is called every time a C is constructed. A static initializer block would only be called once for the JVM.
Its basic OOP. You have to make a public static method and call it. That method can then call the constructor, or you can call the constructor directly from main.
Before you call the constructor, the object don't exist, therefore no instance methods exist, therefore nothing tied to the instance/object can be called. The only things that do exist before the constructor is called is the static methods.
Following way seems to achieve what is required. Without using static methods/variables
namespace FnCallBeforeConstructor
{
static void Main(string[] args)
{
MyClass s = new MyClass();
Console.ReadKey();
}
partial class MyClass: Master
{
public override void Func()
{
Console.WriteLine("I am a function");
}
public MyClass()
: base()
{
Console.WriteLine("I am a constructor");
}
}
class Master
{
public virtual void Func() { Console.WriteLine("Not called"); }
public Master()
{
Func();
}
}
}
Output is:
I am a function
I am a constructor
public class MyClass<T>
{
public static readonly String MyStringValue;
static MyClass()
{
MyStringValue = GenerateString();
}
private static String GenerateString()
{
//Dynamically generated ONCE per type (hence, not const)
}
public void Foo()
{
Console.WriteLine(MyStringValue);
}
}
It's my understanding that the static readonly String won't get generated until the static constructor is called on the class. But, the static constructor won't be called until one of the static methods or variables is accessed.
In a multi-threaded environment is it possible to run into issues because of this? Basically, is the static constructor by default singleton locked or do I have to do this myself? That is... do I have to do the following:
private static Object MyLock;
static MyClass()
{
lock(MyLock)
{
if (MyStringValue == null)
MyStringValue = GenerateString();
}
}
The static constructor is guaranteed to run only once per instantiated type. So you don't need your locking.
Note that it will run once for each generic parameter. And the static fields on the generic class aren't shared between different generic parameters either.
To avoid this why not make the value a static property with only a get accessor which returned the cached value, which you could then make private? Accessing the property get would assure the static constructor ran first.