简体   繁体   English

从 FieldInfo 获取 Object 个实例

[英]Get Object Instances from FieldInfo

I'm trying to call a method for each of the variables/instances of a given type in my class. I've found other posts describing a way to do this using reflection.我正在尝试为我的 class 中给定类型的每个变量/实例调用一个方法。我发现其他帖子描述了使用反射执行此操作的方法。 However, the examples I have found are using Activator.CreateInstance() or with only one instance of the given class (using FieldInfo.GetValue() ).但是,我发现的示例正在使用Activator.CreateInstance()或仅使用给定 class 的一个实例(使用FieldInfo.GetValue() )。 I would like to call this method on the instances themselves, rather than creating a new instance and calling the method.我想在实例本身上调用此方法,而不是创建一个新实例并调用该方法。 Is this possible?这可能吗?

Example of what I'm trying to do:我正在尝试做的事情的例子:

public class Data
{
    int x;
    public Data(int x){
        this.x = x;
    }

    public void Print()
    {
        Console.WriteLine(x);
    }
}

public class MyClass
{
    private Data instance1 = new Data(5);
    private Data instance2 = new Data(4);

    ...

    public void PrintAllX(){

        var fields = GetType().GetFields(BindingFlags.NonPublic | BindingFlags.Instance).Where(f => f.FieldType == typeof(Data));
        foreach(FieldInfo field in fields)
        {
            MethodInfo method = field.FieldType.GetMethod("Print");
            var instance = ?;// need to get 'Data' instance for each field here (instance1, instance2)
            method?.Invoke(instance, null);
        }
    }
}

I've tried setting instance equal to field.GetValue(null) for this as suggested in this post , but it did not work giving me the error: TargetException: Non-static field requires a target .我已经尝试按照这篇文章中的建议为此将实例设置为field.GetValue(null) ,但它不起作用并给我错误: TargetException: Non-static field requires a target

Thanks to madreflection's suggestion I was able to come up with a solution for my problem.感谢madreflection 的建议,我能够为我的问题想出一个解决方案。 Here's the solution to the example code from my question.这是我的问题中示例代码的解决方案。 Note that as mentioned in his comment, using a collection may be better for subsequent calls.请注意,正如他的评论中提到的,使用集合对于后续调用可能更好。 However, in my case I am only ever calling this method once so the performance of subsequent calls isn't a problem.但是,在我的例子中,我只调用一次此方法,因此后续调用的性能不是问题。

public void PrintAllX()
    {

        List<object> fieldObjs = GetType().GetFields(BindingFlags.NonPublic | BindingFlags.Instance).Select(s => s.GetValue(this)).ToList();
        foreach (object obj in fieldObjs)
        {
            if (obj == null) continue;

            if (obj.GetType() == typeof(Data))
                ((Data)obj).Print();
        }
    }

Perhaps I am missing something.. but reflection may not be the right tool here.也许我遗漏了一些东西……但反思可能不是这里的正确工具。

Instead of making each of your Data fields separate variables, what if you put them in a collection.. then you can avoid reflection entirely.与其让每个Data字段都成为单独的变量,不如将它们放在一个集合中会怎样……那么您就可以完全避免反射。

Something like:就像是:

public class MyClass {
    private Data instance1 = new Data(5);
    private Data instance2 = new Data(4);

    private List<Data> datas = new List<Data> {
        instance1,
        instance2    // etc...
    };

    public void PrintAllX() {
        foreach(Data data in datas) {
            data.Print();
        }
    }
}

Update: modified code to be a hybrid - field variables, with a List of those field variables.更新:将代码修改为混合字段变量,其中包含这些字段变量的列表。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM