【问题标题】:Reflection Field Accessor, get property value反射字段访问器,获取属性值
【发布时间】:2012-08-08 15:46:57
【问题描述】:

我有一个 Human 类,需要获取“IsChecked”值。 ItemsSource 可能有不同的类型,但所有类都有 IsChecked 属性。

public class Human{
    public bool IsChecked{
      get;
      set;
    }
}

private void CheckBoxLoaded(object sender, RoutedEventArgs e) //sender is CheckBox
    //How set value from IsChecked?
    var prop = t.GetType().GetProperties().Single(n => n.Name == "IsChecked");//I can access it by this method, but can't set value of sender which CheckBox;
}

【问题讨论】:

  • 我已回滚您的编辑。你没有把答案放在问题中。如果您有答案,请将其作为答案发布。否则,请接受解决您问题的用户回答。

标签: c# windows-phone-7 reflection properties


【解决方案1】:

我假设由于某种原因你不能重构你的Human 类来实现一些ICheckable 接口,包含IsChecked,对吧?

如果您使用的是 C# 4.0,另一种选择是使用 dynamic 数据类型,这将允许您设置仅在运行时检查的属性:

private void CheckBoxLoaded(object sender, RoutedEventArgs e) {
     dynamic dynamicObject  = (sender as FrameworkElement).Tag;
     bool checkedState = dynamicObject.IsChecked;
}

如果所有其他方法都失败了并且您真的必须使用反射,那么您已经完成了 90% 的工作。您只需调用PropertyInfo 对象的GetValue 方法,为其提供您希望从中检索值的实例:

PropertyInfo prop = t.GetType().GetProperty("IsChecked"); // Simpler.
var isChecked = prop.GetValue(t, null);
(sender as CheckBox).IsChecked = isChecked;

【讨论】:

  • prop.SetValue(t, true, null); //为上下文中的所有复选框设置值Checked,但是如何从发件人那里检索它? Sender.Tag 包含具有 IsChecked 属性的类
  • 啊,我误会了。我以为你想设置值。我会更新答案。
  • 我想从 sender.Tag 中获取值并将 IsChecked 设置为 CheckBox。
  • 我使用的是您在 OP 中使用的 t,但我再次更改了它,现在我知道您正在尝试从 sender 获取 Tag 属性。
  • OP 是“原始帖子”,您的原始问题。现在有什么不清楚的地方?
【解决方案2】:

我建议重构它以使用基类或至少一个接口。但是,如果这不可能,简单地使用 dynamic 就可以解决问题:

dynamic obj = t;
bool value = t.IsChecked;

【讨论】:

  • Windows Phone 不支持动态
【解决方案3】:

这将切换状态:

private void CheckBoxLoaded(object sender, RoutedEventArgs e)
{
        var prop = e.GetType().GetProperty("IsChecked", 
                   BindingFlags.Instance | BindingFlags.Public);
        // read the current value
        var current = (bool)prop.GetValue(sender, null);
        //and toggle it
        prop.SetValue(sender, !current, null);
} 

虽然重构为基础/接口可能会更干净,而且性能肯定更好。如果它总是一个 CheckBox,那么这也是简单的路线:

private void CheckBoxLoaded(object sender, RoutedEventArgs e)
{
        var c = sender as CheckBox;
        // read the current value
        var current = c.IsChecked;
        //and toggle it
        c.IsChecked = !current;
} 

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2017-05-14
    • 2013-04-24
    • 1970-01-01
    • 2011-10-06
    • 2011-10-02
    • 2012-11-04
    相关资源
    最近更新 更多