Anteckning
Åtkomst till den här sidan kräver auktorisering. Du kan prova att logga in eller ändra kataloger.
Åtkomst till den här sidan kräver auktorisering. Du kan prova att ändra kataloger.
Interesting fact that I discovered today: usually, static field initializers run whenever the parent type is first loaded. However when you ngen the assembly, apparently you can load the type and work with it – static field initializers will only be executed immediately before you actually access the field.
I’ve run into this by having a static Stopwatch timer = Stopwatch.StartNew(); in one of my types. It was supposed to measure an application’s startup time, but I noticed that after NGEN’ing the assembly the timer always returned a value close to 0.
Here’s the code to verify this behavior:
using System;
class Program
{
private static int field = Initialize("Field initializer");
static void Main(string[] args)
{
Initialize("Main");
field = 1; // touch the field
}
private static int Initialize(string message)
{
Console.WriteLine(message + ": " + DateTime.Now.Ticks.ToString());
return 0;
}
}
This works the same for .NET 4.0 SP1 for Debug/Release and x86/x64. I didn’t try other frameworks/OS/platforms.
Here’s the output from the console:
E:\>NgenedStaticFieldInitializers.exe
Field initializer: 634462768999291588
Main: 634462768999321594
E:\>NgenedStaticFieldInitializers.exe
Field initializer: 634462769013544438
Main: 634462769013574444
E:\>ngen install NgenedStaticFieldInitializers.exe
Microsoft (R) CLR Native Image Generator - Version 4.0.30319.1
Copyright (c) Microsoft Corporation. All rights reserved.
Installing assembly E:\NgenedStaticFieldInitializers.exe
1> Compiling assembly E:\NgenedStaticFieldInitializers.exe (CLR v4.0.30319) .
..
1>NgenedStaticFieldInitializers, Version=1.0.0.0, Culture=neutral, PublicKeyToke
n=null
E:\>NgenedStaticFieldInitializers.exe
Main: 634462769095630852
Field initializer: 634462769095660858
E:\>NgenedStaticFieldInitializers.exe
Main: 634462769108903506
Field initializer: 634462769108933512
Comments
Anonymous
July 14, 2011
I believe all static field initializers will run at the same time - but when that occurs is only guaranteed to be "before the first static field access or constructor call" unless you've got a static constructor, which changes the timing a bit. All of this changed (in implementation) in .NET 4 - I wasn't aware that ngen makes the situation even more complicated though. I wonder whether that is mostly about the entry point type rather than other types... Here's my write-up from a while ago: msmvps.com/.../type-initialization-changes-in-net-4-0.aspxAnonymous
July 15, 2011
From what I understand, and I can't find the blog post that i always refer to when dealing with static initializers, is that the timing of static field initializers is undefined unless you have a static constructor. The only thing that is guarenteed without a static constructor is that the field will be initialized before it's first accessed. With a static constructor the static fields are initialized before the static contructor is executed. This all has something to do with BeforeFieldInit, and this post is the closest I found to a decent explanation : www.satyakomatineni.com/.../displayAnonymous
July 26, 2011
Thanks for the great info, guys!