C# 我正在寻找用于运行时属性替换的 Lamba / Expression / Func / Reflection 的什么构造?

发布于 2024-12-07 15:43:53 字数 567 浏览 0 评论 0原文

我在通用基类上有一个方法,我想对其所有超类执行该

方法逻辑类似于:

BuildAverageDateStats(List<type> items, DateProperty1 exp, DateProperty2 exp2)
{
 return new Stat{ 
  Value = items.Average(c => (c.DateProperty2 - c.DateProperty1).Milliseconds)
 };
}

myobject.BuildAverageDateStats(list, () => c.QueuedDate, () => c.CompletedDate);
myobject.BuildAverageDateStats(list, () => c.ActionedDate, () => c.CompletedDate);

我认为我需要表达式,但不确定如何...

我可以将其作为 Func ie 发送Value = items.Average(c => myfunc(c)) 但正在寻找属性替换示例。

I've a method on a generic base class that I want to execute for all superclasses of it

The logic is something like:

BuildAverageDateStats(List<type> items, DateProperty1 exp, DateProperty2 exp2)
{
 return new Stat{ 
  Value = items.Average(c => (c.DateProperty2 - c.DateProperty1).Milliseconds)
 };
}

myobject.BuildAverageDateStats(list, () => c.QueuedDate, () => c.CompletedDate);
myobject.BuildAverageDateStats(list, () => c.ActionedDate, () => c.CompletedDate);

I think I need expressions, but not sure how...

I could send it in as Func i.e. Value = items.Average(c => myfunc(c)) but looking for a property substitution example.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

肥爪爪 2024-12-14 15:43:53
Stat BuildAverageDateStats<U>(List<type> items, Func<U, double> exp)
where U:type
{
 return new Stat{ 
  Value = items.OfType<U>().Average(exp);
 };
}

你可以这样称呼它

BuidlAverageDateStats<Dog>(items, d=>d.Age - d.Height);

虽然我的例子没有意义。

Stat BuildAverageDateStats<U>(List<type> items, Func<U, double> exp)
where U:type
{
 return new Stat{ 
  Value = items.OfType<U>().Average(exp);
 };
}

You can call it like this

BuidlAverageDateStats<Dog>(items, d=>d.Age - d.Height);

Though my example doesn't make sense.

独自唱情﹋歌 2024-12-14 15:43:53

如果您真的只打算使用现在拥有的三个 DateTime 属性之一,我将保留您现在拥有的方法签名。
为了使事情变得更简洁,请在您的类上为您的属性创建一些公共静态只读委托字段,并使用这些字段,而不是一次又一次地编写相同的表达式:

    public static readonly DateSelector Date1Property = delegate(CompareTest c) { return c.Date1; };
    public static readonly DateSelector Date2Property = delegate(CompareTest c) { return c.Date2; };
    public static readonly DateSelector Date3Property = delegate(CompareTest c) { return c.Date3; };

另一方面,如果您希望继承类实现比其他类更多的属性对于您现在拥有的三个属性,您可以考虑将属性作为字符串传递,并使用动态 Linq 库(并构建返回属性的动态表达式)或 DynamicMethod 来返回属性。两者都会从痛苦的表现中得到反思的好处。如果您需要它,我有一些代码可供使用。
不过,类型安全将被排除在外,因此除非必要,否则我不会使用它,而且听起来似乎并非如此。

门诺

If you are really only ever going to use one of the three DateTime properties that you have right now, I would keep the method signature the way you have it right now.
To make things neater, make some public static readonly delegate fields on your class for your properties, and use those, instead of writing the same expression time and time again:

    public static readonly DateSelector Date1Property = delegate(CompareTest c) { return c.Date1; };
    public static readonly DateSelector Date2Property = delegate(CompareTest c) { return c.Date2; };
    public static readonly DateSelector Date3Property = delegate(CompareTest c) { return c.Date3; };

If, on the other hand, you expect inheriting classes to implement more properties than the three you have right now, you could consider passing in the properties as String and using the Dynamic Linq Library (and build a dynamic expression that returns the property) or a DynamicMethod to return your property. Both would have the benefits of reflection with the painful performance. If you need it, I have some code laying around for that.
Type safety will be out the window though, so I wouldn't use it unless necessary, and it sounds like it isn't.

Menno

轮廓§ 2024-12-14 15:43:53
static Stat BuildAverageDateStats<T>(List<T> items, string pname1, string pname2){
    return new Stat { 
        Value = items.Average( c => 
        {
            var ty = c.GetType();
            var pv1 = (dynamic)ty.GetProperty(pname1).GetValue(c,null);
            var pv2 = (dynamic)ty.GetProperty(pname2).GetValue(c,null);
            return pv2 - pv1;
        })
    };
}
static Stat BuildAverageDateStats<T>(List<T> items, string pname1, string pname2){
    return new Stat { 
        Value = items.Average( c => 
        {
            var ty = c.GetType();
            var pv1 = (dynamic)ty.GetProperty(pname1).GetValue(c,null);
            var pv2 = (dynamic)ty.GetProperty(pname2).GetValue(c,null);
            return pv2 - pv1;
        })
    };
}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文