【问题标题】:c# Reflection of a nested struct propertyc#嵌套结构属性的反射
【发布时间】:2012-11-07 15:48:20
【问题描述】:

我正在尝试对对象解析执行一些动态文本,但是,在为结构创建和设置嵌套属性值时遇到了问题。

如果我在一个结构对象中有一个属性,那么每当我使用反射来获取结构对象并设置它的任何属性/字段时,对象上的值都不会改变。取下面的对象图。

public struct MyStruct
{
    public int MyIntProp {get;set;}
}

public class MyObj
{
    public MyStruct NestedStruct {get;set;}
}

PropertyInfo pInfo = (myObj.GetType()).GetProperty("NestedStruct");
object nestedStruct = pInfo.GetValue(myObj); // This is the nested struct however it is only a copy not the actual object
PropertyInfo intInfo = (pInfo.PropertyType).GetProperty("MyIntProp");
intInfo.SetValue(nestedStruct, 23); // this sets the MyIntProp on the nestedStruct, but it is not set on the myObj.NestedStruct.  My goal is to set object on that NestedStruct via reflection.

当我使用反射获取 NestedStruct 属性然后在该结构上设置 MyIntProp 时,原始 MyObj.NestedStruct.MyIntProp 不会改变。自然,我将此归因于结构是值类型而不是引用类型的事实。

所以真正的问题是如何使用反射来获取对值类型的引用。

【问题讨论】:

  • 有没有机会避免使用可变结构?
  • 这真的是我正在制作的一个库,它允许将分隔文件解析为动态对象。到目前为止,它适用于纯引用类型对象。但是,当进入值类型容器时,我似乎遇到了这个问题。
  • 所以不要使用“值类型容器”。基本上,可变结构只是坏消息。
  • 我明白了。我正在进行的项目涉及运动模拟。因此,我有包含纯值类型(主要是双精度值)的运动对象。当时我认为使运动对象不可变将有利于防止任何调用方法损坏原始数据。也许这是使用结构的错误推理?我觉得它们类似于 DateTime 或 TimeSpan 对象。
  • 使用结构可能很好(没有更多上下文我无法判断) - 但您给出的示例显然 不是 不可变的!

标签: c# .net reflection


【解决方案1】:

如果我在一个结构体对象中有一个属性,那么每当我使用反射来获取结构体对象并设置它的任何属性/字段时,对象上的值都不会改变。

嗯,不——因为在这一行:

object nestedStruct = pInfo.GetValue(myObj);

...您正在复制该值,因为它是一种值类型。您也在装箱 - 这很好,因为这意味着当您在 intInfo.SetValue 调用中对其进行变异时,它是被修改的装箱副本。 (如果你在打电话给intInfo.SetValue 的时候打它,那真是没救了。)

在盒装副本中进行更改后,您需要将其设置back到对象的属性中:

pInfo.SetValue(myObject, nestedStruct);

尝试使用反射做你正在做的事情会很有启发性:

MyObj myObj = new MyObj();
myObj.NestedStruct.MyIntProp = 23;

编译器会在最后一行给你一个错误,解释这是一件愚蠢的事情:

Test.cs(20,9): 错误 CS1612: 无法修改 'MyObj.NestedStruct' 的返回值,因为它不是变量

【讨论】:

  • 在我使用结构体的所有时间里,我从未遇到过这种情况。我不太确定我明白为什么。您能否指出一些可能解释为什么它不是变量的文档?
  • 想了想,就明白为什么它不是一个变量,它是一组属性而不是字段。
  • @galford13x:很高兴我不需要尝试进入它 :)(我才刚刚看到你之前的评论,恐怕。)
猜你喜欢
  • 2023-04-10
  • 1970-01-01
  • 2018-07-19
  • 2021-09-18
  • 1970-01-01
  • 2020-01-19
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多