zoukankan      html  css  js  c++  java
  • 透视Datatable

    源代码:/Files/zhuqil/PivotDataTable.zip 

       现在,以表格的形式显示的数据是任何应用程序的重要组成部分。但有时你需要以数据行格式显示大量的数据。如果行数巨大,它变得非常难以分析。在这种情况下,您可能希望使用其他格式统计你的数据,如: charts, graphs, groups, pivots等 。本文将介绍一种使用适当的聚合函数的方式来透视你的数据,它可以很容易提高您的报表功能。

        下面的截图是在GridView中显示的数据透视功能。(关于数据透视还可以参考:ASP.NET实现类似Excel的数据透视表

        为了简化方案,我把表的结果分三个区域显示:RowField, DataField, 和ColumnFields,除了这些,Pivot类提供一些供您来选择的聚合函数来绑定的数据。可提供的选项有:

    • Count: 返回匹配的数据数量
    • Sum: 返回匹配的数据总和(为了得到总和,将DataField的类型必须转换为decimal类型)
    • First: 返回匹配的数据第一项
    • Last: 返回匹配的数据最后一项
    • Average: 返回匹配的数据平均(为了得到平均值,将DataField的类型必须转换为decimal类型)
    • Max: 返回匹配的数据最大值
    • Min: 返回匹配的数据最小值
    • Exists: 如果有匹配的数据,返回“true”,否则“false”

          代码主要包含了一个名字为"Pivot"的类,在它的构造函数中创建DataTable。 ColumnFields 是一个字符串数组参数,它允许你透视多列数据。这个类还包含了一个实际透视你数据的PivotData() 方法。

      代码
      public DataTable PivotData(string RowField, string DataField, 
             AggregateFunction Aggregate, 
      params string[] ColumnFields)
      {
          DataTable dt 
      = new DataTable();
          
      string Separator = ".";
          var RowList 
      = (from x in _SourceTable.AsEnumerable() 
              select 
      new { Name = x.Field<object>(RowField) }).Distinct();
          var ColList 
      = (from x in _SourceTable.AsEnumerable() 
                         select 
      new { Name = ColumnFields.Select(n => x.Field<object>(n))
                             .Aggregate((a, b) 
      => a += Separator + b.ToString()) })
                             .Distinct()
                             .OrderBy(m 
      => m.Name);

          dt.Columns.Add(RowField);
          
      foreach (var col in ColList)
          {
              dt.Columns.Add(col.Name.ToString());
          }

          
      foreach (var RowName in RowList)
          {
              DataRow row 
      = dt.NewRow();
              row[RowField] 
      = RowName.Name.ToString();
              
      foreach (var col in ColList)
              {
                  
      string strFilter = RowField + " = '" + RowName.Name + "'";
                  
      string[] strColValues = 
                    col.Name.ToString().Split(Separator.ToCharArray(), 
                                              StringSplitOptions.None);
                  
      for (int i = 0; i < ColumnFields.Length; i++)
                      strFilter 
      += " and " + ColumnFields[i] + 
                                   
      " = '" + strColValues[i] + "'";
                  row[col.Name.ToString()] 
      = GetData(strFilter, DataField, Aggregate);
              }
              dt.Rows.Add(row);
          }
          
      return dt;
      }

           首先,该函数通过获取RowList的Distinct的值,确定行的成员;通过获取ColList的Distinct值,确定列的成员。然后,创建datatable的列。然后根据所提供的聚合函数,遍历每一行和获取匹配值到相应的单元格上。调用GetData()函数,检索匹配值。

      代码
      private object GetData(string Filter, string DataField, AggregateFunction Aggregate)
      {
          
      try
          {
              DataRow[] FilteredRows 
      = _SourceTable.Select(Filter);
              
      object[] objList = 
               FilteredRows.Select(x 
      => x.Field<object>(DataField)).ToArray();

              
      switch (Aggregate)
              {
                  
      case AggregateFunction.Average:
                      
      return GetAverage(objList);
                  
      case AggregateFunction.Count:
                      
      return objList.Count();
                  
      case AggregateFunction.Exists:
                      
      return (objList.Count() == 0? "False" : "True";
                  
      case AggregateFunction.First:
                      
      return GetFirst(objList);
                  
      case AggregateFunction.Last:
                      
      return GetLast(objList);
                  
      case AggregateFunction.Max:
                      
      return GetMax(objList);
                  
      case AggregateFunction.Min:
                      
      return GetMin(objList);
                  
      case AggregateFunction.Sum:
                      
      return GetSum(objList);
                  
      default:
                      
      return null;
              }
          }
          
      catch (Exception ex)
          {
              
      return "#Error";
          }
          
      return null;
      }

           这个函数首先过滤到DataRow []数组中匹配RowField和ColumnFields数据 ,然后调用相应的聚合函数。

       如何使用代码:

          代码使用起来很简单。创建一个Pivot类的实例,然后使用要求的参数调用PivotData方法。PivotData()方法返回DataTable,他可直接作为GridView的数据源。

      代码
      DataTable dt = ExcelLayer.GetDataTable("_Data\\DataForPivot.xls""Sheet1$");
      Pivot pvt 
      = new Pivot(dt);

      grdPivot.DataSource 
      = pvt.PivotData("Designation""CTC"
         AggregateFunction.Max, 
      "Company""Department""Year");
      grdPivot.DataBind();

          示例中使用的数据库是一个Excel Sheet ,放在示例应用程序的根文件夹下的“_Data”文件夹中。

          该MergeHeader函数创建合并头部的单元格,并提供了一个简化的外观。

      代码
      private void MergeHeader(GridView gv, GridViewRow row, int PivotLevel)
      {
          
      for (int iCount = 1; iCount <= PivotLevel; iCount++)
          {
              GridViewRow oGridViewRow 
      = new GridViewRow(00
                DataControlRowType.Header, DataControlRowState.Insert);
              var Header 
      = (row.Cells.Cast<tablecell>()
                  .Select(x 
      => GetHeaderText(x.Text, iCount, PivotLevel)))
                  .GroupBy(x 
      => x);

              
      foreach (var v in Header)
              {
                  TableHeaderCell cell 
      = new TableHeaderCell();
                  cell.Text 
      = v.Key.Substring(v.Key.LastIndexOf(_Separator) + 1);
                  cell.ColumnSpan 
      = v.Count();
                  oGridViewRow.Cells.Add(cell);
              }
              gv.Controls[
      0].Controls.AddAt(row.RowIndex, oGridViewRow);
          }
          row.Visible 
      = false;
      }

          该函数为每个PivotLevel创建新行,和相应的合并。 PivotLevel这里是列上的轴完成的数量。

          Header从一个数组中得到所有的列值,对GetHeaderText()返回的重复的值进行分组,根据HeaderText的重复数量,设置新创建的单元格的ColumnSpan属性。将单元格添加到GridViewRow中。最后添加GridViewRowGridView。GetHeaderText() 函数根据PivotLevel返回header text.

          例如,假设一个透视表,完成三个ColumnField: Company, Department, 和Year。GridView的初始化时候,头部将拥有Company.Department。PivotLevel 1是Year。 GetHeaderText()将返回Company。对于PivotLevel 2,GetHeaderText()将返回Company.Department。对于PivotLevel 3,GetHeaderText()将返回Company.Department.Year,等等...

    • 以下是GridView的截图,包含三个层次透视数据:

    •     代码帮助您合并你想要的格式GridView的头单元格。对于初学者,在ExcelLayer.GetDataTable()方法将是一个从Excel表中的中获得数据例子。

          目前,代码只在DataTable中透视数据。该代码将得到加强,将来透视IListSource或ICollection派生的任何对象。

    • 参考原文:http://www.codeproject.com/KB/aspnet/PivotDataTable.aspx



    (全文完)


    以下为广告部分

    您部署的HTTPS网站安全吗?

    如果您想看下您的网站HTTPS部署的是否安全,花1分钟时间来 myssl.com 检测以下吧。让您的HTTPS网站变得更安全!

    SSL检测评估

    快速了解HTTPS网站安全情况。

    安全评级(A+、A、A-...)、行业合规检测、证书信息查看、证书链信息以及补完、服务器套件信息、证书兼容性检测等。

    SSL证书工具

    安装部署SSL证书变得更方便。

    SSL证书内容查看、SSL证书格式转换、CSR在线生成、SSL私钥加解密、CAA检测等。

    SSL漏洞检测

    让服务器远离SSL证书漏洞侵扰

    TLS ROBOT漏洞检测、心血漏洞检测、FREAK Attack漏洞检测、SSL Poodle漏洞检测、CCS注入漏洞检测。

  • 相关阅读:
    (一)Sturts2概述
    day18,常用的模块,os,sys...等
    day17,模块的导入
    day16
    day15
    day14
    day13
    day12
    day11
    day10
  • 原文地址:https://www.cnblogs.com/zhuqil/p/PivotDataTable.html
Copyright © 2011-2022 走看看