在 C# 中使用 LINQ select 作为方法参数

Use LINQ select as method parameter in C#

我正在尝试为 HTML table 构建创建通用方法。

作为我需要的功能的一部分,我希望用户能够指定将变成列的属性。

因为这是一个通用方法,我原以为用户可以将他们需要的属性作为某种 LINQ 表达式传递,然后我将把这个 select 应用到数据集,然后循环通过属性构建 table 数据:

  public static string BuildCollapsibleHtmlTable<T>(
        IEnumerable<T> dataSet,
        Func<T, object> tableDataColumnDefinitions,
        KeyValuePair<string, string>[] tableColumnNames,
        Func<T, object> groupByQuery,
        Func<T, decimal> groupSumQuery) where T : class, new() {

      ... implementation ..
   }

'tableColumnDefinitions' 部分是我挣扎的地方(第二个参数)。我可以让它用于分组和求和,但不能用于 selecting columns/properties 在 table:

中使用
var test = HtmlBuilders.BuildCollapsibleHtmlTable<Client>(
               Model.Clients,
               (clients => clients.ClientName),
               new KeyValuePair<string, string>[] { 
                   new KeyValuePair<string, string> ("Client", "tdCSSLeft"),
                   new KeyValuePair<string, string> ("Debt", "tdCSSCenter")
                },
               (client => client.ClientName),
               (client => client.TotalDebt)
           );

我似乎只能让它工作一次 属性(因此我需要一个表达式数组)。我不反对这个,但想知道我这样做是不是错了?是否有 easier/better 方法将任意 select 查询作为参数传递?

是的,您需要使用数组。请注意,您似乎已经有一个类似的数组:KeyValuePair<string, string>[] tableColumnNames,所以我看不出问题出在哪里。

从技术上讲,您可以通过这种方式更改方法的签名:

public static string BuildCollapsibleHtmlTable<T>(
    IEnumerable<T> dataSet,
    KeyValuePair<string, string>[] tableColumnNames,
    Func<T, object> groupByQuery,
    Func<T, decimal> groupSumQuery,
    params Func<T, object>[] tableDataColumnDefinitions
) where T : class, new() {

这样调用方法时就不需要创建数组了,但是可以这样调用

var test = HtmlBuilders.BuildCollapsibleHtmlTable<Client>(
           Model.Clients,
           //new KeyValuePair<string, string>[] { 
           new[] {  // Shorter
               new KeyValuePair<string, string> ("Client", "tdCSSLeft"),
               new KeyValuePair<string, string> ("Debt", "tdCSSCenter")
           },
           (client => client.ClientName),
           (client => client.TotalDebt),

           // tableDataColumnDefinitions
           (clients => clients.ClientName),
           (clients => clients.ClientSurname),
           (clients => clients.ClientAddress)
       );