I'm trying to get filed values in a nested static class by this simple code:
public static class DataConstants {
public static class Roles {
public static readonly Role[] All = new Lazy<Role[]>(LoadAllRoles).Value;
private static Role[] LoadAllRoles() {
var fields = typeof(DataConstants.Roles)
.GetFields(BindingFlags.Public | BindingFlags.Static);
foreach (var field in fields) {
var r = field.GetValue(null);
}
return blah-blah;
}
public static readonly Role Role1 = new Role {
Id = -1,
Name = "role1",
};
public static Role Role2 = new Role {
Id = -2,
Name = "role2",
};
}
}
Everything seems to be fine and I think this should work. But calling the field.GetValue(null)
always returns null
. Have you any idea what I missed here? Thanks in advance.
Welcome to the wonderful world of static initialisation. Static members are initialised in the order that they're declared, and All
is declared before Role1
or Role2
. So Role1
and Role2
aren't assigned until after All
is assigned.
Note that your use of Lazy<T>
here is pointless: you're immediately calling .Value
, which means that LoadAllRoles
is called during the initialisation of All
. If All
was actually a Lazy<T>
(or was a property which wrapped a Lazy<T>
), and Lazy<T>.Value
was only called after Role1
and Role2
were initialised, you wouldn't see this issue.
You can move the declarations of Role1
and Role2
to the top of the type, above All
, which "fixes" the issue. You'd be better off assigning All
inside a static constructor though, as this is less prone to accidental breakage:
public static class DataConstants {
public static class Roles {
public static readonly Role[] All;
static Roles()
{
All = LoadAllRoles();
}
private static Role[] LoadAllRoles() {
var fields = typeof(DataConstants.Roles)
.GetFields(BindingFlags.Public | BindingFlags.Static);
foreach (var field in fields) {
var r = field.GetValue(null);
Console.WriteLine("field: " + r);
}
return new Role[0];
}
public static readonly Role Role1 = new Role {
Id = -1,
Name = "role1",
};
public static Role Role2 = new Role {
Id = -2,
Name = "role2",
};
}
}
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.