为什么我不能从嵌套类属性中获取布尔值?

Why can't I get the boolean value from nested classes property?

提问人:dezox 提问时间:7/29/2022 最后编辑:Tim Schmelterdezox 更新时间:7/29/2022 访问量:192

问:

我正在尝试使用 PropertyInfo 的 GetValue() 方法,但似乎它不起作用。

public bool IsDeviceOperable(ServiceType type, bool isServer, string domain)
{
    string settingsFileContent = _fileReader.Read(_filePathProvider.GetSettingsFilePath());

    var settings = _jsonDeserializer.Deserialize<Settings>(settingsFileContent);
    var settingsName = GetSettingsNameByType(type);

    string deviceType = GetDeviceType(isServer);

    var info = settings.GetType().GetProperty(domain.ToUpper())
        .PropertyType.GetProperty(settingsName)
        .PropertyType.GetProperty(deviceType);


    bool value = (bool)info.GetValue(settings, null);

    return value;
}

它引发 System.Reflection.TargetException: 'Object does not match target type.'

我的设置文件如下所示:

public class Settings
{
    public FirstDomain First { get; set; }
    public SecondDomain Second { get; set; }
    ...
}

域类如下所示:

public class FirstDomain
{
    public Settings1 firstSettings { get; set; }
    public Settings2 secondSettings { get; set; }
    ...
}

public class SecondDomain
{
    public Settings1 firstSettings { get; set; }
    public Settings2 secondSettings { get; set; }
    ...
}

设置类如下所示:

public class Settings1
{
    public bool RunOnClient { get; set; }
    public bool RunOnServer { get; set; }
}

public class Settings2
{
    public bool RunOnClient { get; set; }
    public bool RunOnServer { get; set; }
}

请不要评论类的结构,它必须是这样的。第一域第二域是有原因的,而且设置也各不相同,为了便于理解,我重命名了它们。

C# 反射 嵌套 PropertyInfo

评论

0赞 Markus 7/29/2022
什么?错误消息指向实例不是声明属性的类型( 或 )。domainSettingsSettings1Settings2
0赞 dezox 7/29/2022
@Markus对不起,忘了更改它。它只是设置。
0赞 dezox 7/29/2022
PropertyInfo 如下所示:var info = settings。GetType() 中。GetProperty(第一个域) 。PropertyType.GetProperty(设置1) 。PropertyType.GetProperty(RunOnClient);属性信息很好,它找到了布尔值,但我无法获得它的值。

答:

2赞 Markus 7/29/2022 #1

问题在于,代码为嵌套属性创建属性信息,但提供了父对象的实例。属性信息始终对定义属性的类型的实例进行操作。

因此,必须先获取父实例,然后在正确的实例上调用该属性:

var settings = _jsonDeserializer.Deserialize<Settings>(settingsFileContent);
var settingsName = GetSettingsNameByType(type);

string deviceType = GetDeviceType(isServer);

var domainProp = settings.GetType().GetProperty(domain.ToUpper());
var domainInst = domainProp.GetValue(settings, null);
var settingsProp = domainProp
    .PropertyType.GetProperty(settingsName);
var settingsInst = settingsProp.GetValue(domainInst, null);
var deviceTypeProp = settingsProp
    .PropertyType.GetProperty(deviceType);

bool value = (bool)deviceTypeProp.GetValue(settingsInst, null);