如何对对象列表的特定字段求和 [英] how to sum particular field of list of Objects

查看:372
本文介绍了如何对对象列表的特定字段求和的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

嗨朋友们,

我需要对对象列表的特定字段求和。我编写了一个接受列表但不知道如何传递字段名称的方法。

例如,如果我传递 MarketValue 它应该返回MarketValue总和如果我通过数量它应该返回数量总和



这是我的班级

Hi Friends,
I need to sum particular field of list of Objects. I have written a method with accepts Lists but don't know how to pass the field name.
For Example if i pass MarketValue it should return MarketValue Sum like wise if i pass Quantity it should return Quantity Sum

This is my class

public class TopList
   {
        public static double marketsum = 1;
        public string Symbol{get;set;}
        public double MarketValue{get;set;}
        public double PreviousMarketVale{get;set;}
        public double Quantity{get;set;}
        public double MarketValuePercentage { get { return Math.Round((MarkrtValue / marketsum) * 100,2); } }
        public double ChangeInMarketValue {get { return Math.Round(((MarkrtValue-PreviousMarketVale)/MarkrtValue)*100,2);}}
   }





我的方法



My Method

public static double MarketSum(List<TopList>tl)//here it should accept one more paramter
        {
            return tl.Sum(s => s.MarketValue);//here i need to pass different fields
        }





这就是我调用方法的方法



This is how i invoke the method

List<TopList> tl = new List<TopList>();
 double ms = MarketSum(tl);





提前致谢:)



Thanks in advance :)

推荐答案

I只是抽象方法之外的字段选择:

I'd just abstract the field selection outside of the method:
public static double MarketSum(List<TopList>tl, Func<TopList, double> accessor)
{
    return tl.Sum(accessor);
}



将其称为:


Calling it as:

List<TopList> tl = new List<TopList>();
  double ms = MarketSum(tl, s => s.MarketValue);



另一种选择是预先定义访问者功能:


Another option is to pre-define the accessor functions:

private static Dictionary<string, Func<TopList, double>> Accessors = new Dictionary<string, Func<TopList, double>>() {
  { "MarketValue", s => s.MarketValue },
  { "Quantity", s => s.Quantity },
  // etc.
};
public static double MarketSum(List<TopList>tl, string accessorKey)
{
    Func<TopList, double>> accessor;
    if (!Accessors.TryGetValue(accessorKey, out accessor))
      throw new InvalidOperationException("No such accessor: " + accessorKey);
    return tl.Sum(accessor);
}



将其称为:


Calling it as:

List<TopList> tl = new List<TopList>();
  double ms = MarketSum(tl, "MarketValue");



第三种选择是使用反射来自动预定义访问者功能:


A third option is to use reflection to automatically pre-define the accessor functions:

public static Dictionary<string, Func<TopList, double>> Accessors = GetPropertyAccessDictionary<TopList, double>();
static Dictionary<string, Func<Tclass, Tvalue>> GetPropertyAccessDictionary<Tclass, Tvalue>()
{
  Dictionary<string, Func<Tclass, Tvalue>> accessors = new Dictionary<string, Func<Tclass, Tvalue>>();
  PropertyInfo[] props = typeof(Tclass).GetProperties(BindingFlags.Public);
  Type valueType = typeof(Tvalue);
  foreach (var prop in props)
  {
    MethodInfo getter = prop.GetMethod;
    if (valueType.IsAssignableFrom(getter.ReturnType))
      accessors.Add(prop.Name, o => (Tvalue)(getter.Invoke(o, null)));
  }
  return accessors;
}

public static double MarketSum(List<TopList> tl, string accessorKey)
{
  Func<TopList, double> accessor = null;
  if (!Accessors.TryGetValue(accessorKey, out accessor))
    throw new InvalidOperationException("No such accessor: " + accessorKey);
  return tl.Sum(accessor);
}



使用与上面完全相同的内容。

基于字符串的访问者查找不是一个伟大的建筑。如果字符串直接来自用户输入,则可以。即便如此,最好将其解析并验证为更结构化的东西。


Use it exactly the same as above.
The string-based lookup of the accessors is not a great architecture. It's OK if the strings are coming directly from user input. Even then, it's probably better to parse and validate that into something more structured.


我可能会声明另一个类来包含你的列表并在该类中包含sum方法。



I would probably declare another class to contain your list and include the sum methods on that class.

public class TopListItem
{
    public static double marketsum = 1;
    public string Symbol { get; set; }
    public double MarketValue { get; set; }
    public double PreviousMarketVale { get; set; }
    public double Quantity { get; set; }
    public double MarketValuePercentage { get { return Math.Round((MarketValue / marketsum) * 100, 2); } }
    public double ChangeInMarketValue { get { return Math.Round(((MarketValue - PreviousMarketVale) / MarketValue) * 100, 2); } }
}

public class TopList
{
    public static List<toplistitem> items { get; set; }

    static TopList()
    {
        items = new List<toplistitem>();
    }
    public double sumQuantity()
    {
        //Sum them here
        return 0;
    }
}





要调用:



To invoke:

TopList t1 = new TopList();
double totalQuantity = t1.sumQuantity();


这篇关于如何对对象列表的特定字段求和的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆