私dataset
はピボットしてからグリッドビューにバインドしています。ピボットされたテーブルにすべてのitemtemplates
値が存在する場合は正常に機能していますが、ピボットされたテーブルに列が存在しない場合、 gridview をバインドするときにエラーが発生します。列のいずれかが存在しない場合にグリッド ビューでそれを処理する方法を教えてください。ただし、グリッド ビューにバインドしていますitemtemplate
。以下は私のグリッドビューコードです。
<asp:GridView ID="gvCoreUtilization" runat="server" BackColor="White" BorderColor="#cEcFcE"
BorderStyle="Solid" BorderWidth="1px" CellPadding="4" ForeColor="Black" OnRowCreated="grdPivot3_RowCreated"
AutoGenerateColumns="false" OnRowDataBound="grdCoreUtilization_RowDataBound">
<RowStyle BackColor="#F7F7DE" />
<FooterStyle BackColor="#CCCC99" />
<PagerStyle BackColor="#F7F7DE" ForeColor="Black" HorizontalAlign="Right" />
<SelectedRowStyle BackColor="#CE5D5A" Font-Bold="True" ForeColor="White" />
<HeaderStyle BackColor="#6B696B" Font-Bold="True" ForeColor="White" HorizontalAlign="Left" />
<AlternatingRowStyle BackColor="White" />
<Columns>
<asp:TemplateField>
<ItemTemplate>
<asp:Label ID="lblRoleID" Text='<%#Eval("RoleId") %>' runat="server" Visible="false"></asp:Label>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField>
<HeaderTemplate>
SupervisorName
</HeaderTemplate>
<ItemTemplate>
<asp:Label ID="lblSupervisorName" Text='<%#Eval("SupervisorName") %>' runat="server"></asp:Label>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField>
<HeaderTemplate>
UserECode
</HeaderTemplate>
<ItemTemplate>
<asp:Label ID="lblUserECode" Text='<%#Eval("UserECode") %>' runat="server"></asp:Label>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField>
<HeaderTemplate>
UserName
</HeaderTemplate>
<ItemTemplate>
<asp:Label ID="lblUserName" Text='<%#Eval("UserName") %>' runat="server"></asp:Label>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField>
<HeaderTemplate>
Designation
</HeaderTemplate>
<ItemTemplate>
<asp:Label ID="lblDesignation" Text='<%#Eval("Designation") %>' runat="server"></asp:Label>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField>
<HeaderTemplate>
L & D Training%
</HeaderTemplate>
<ItemTemplate>
<asp:Label ID="lblLDTraining" Text='<%#Eval("L & D Training%") %>' runat="server"></asp:Label>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField>
<HeaderTemplate>
Non Production%
</HeaderTemplate>
<ItemTemplate>
<asp:Label ID="lblNonProduction" Text='<%#Eval("Non Production%") %>' runat="server"></asp:Label>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField>
<HeaderTemplate>
Process Support%
</HeaderTemplate>
<ItemTemplate>
<asp:Label ID="lblProcessSupport" Text='<%#Eval("Process Support%") %>' runat="server"></asp:Label>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField>
<HeaderTemplate>
Process Training%
</HeaderTemplate>
<ItemTemplate>
<asp:Label ID="lblProcessTraining" Text='<%#Eval("Process Training%") %>' runat="server"></asp:Label>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField>
<HeaderTemplate>
Production%
</HeaderTemplate>
<ItemTemplate>
<asp:Label ID="lblProduction" Text='<%#Eval("Production%") %>' runat="server"></asp:Label>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField>
<HeaderTemplate>
System Downtime%
</HeaderTemplate>
<ItemTemplate>
<asp:Label ID="lblSystemDowntime" Text='<%#Eval("System Downtime%") %>' runat="server"></asp:Label>
</ItemTemplate>
</asp:TemplateField>
<asp:TemplateField>
<HeaderTemplate>
Grand Total%
</HeaderTemplate>
<ItemTemplate>
<asp:Label ID="lblGrandTotal" Text='<%#Eval("Grand Total%") %>' runat="server"></asp:Label>
</ItemTemplate>
</asp:TemplateField>
</Columns>
</asp:GridView>
実際、、、、、、、、、、、、、itemtemplate にバインドしているピボットされた列です。ユーザーによっては、これらの列のいくつかが存在せず、グリッドのバインド中に"L & D Training%"
エラーが"Non Production%"
発生"Process Support%
します。"Process Training%"
"Production%"
"System Downtime%"
"Grand Total%"
以下は、ピボットを行っているピボットクラスのコードです:-
private DataTable _SourceTable = new DataTable();
private IEnumerable<DataRow> _Source = new List<DataRow>();
public Pivot(DataTable SourceTable)
{
_SourceTable = SourceTable;
_Source = SourceTable.Rows.Cast<DataRow>();
}
public DataTable PivotData(string DataField, AggregateFunction Aggregate, string[] RowFields, string[] ColumnFields)
{
DataTable dt = new DataTable();
string Separator = ".";
var RowList = _SourceTable.DefaultView.ToTable(true, RowFields).AsEnumerable().ToList();
for (int index = RowFields.Count() - 1; index >= 0; index--)
RowList = RowList.OrderBy(x => x.Field<object>(RowFields[index])).ToList();
// Gets the list of columns .(dot) separated.
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(RowFields);
foreach (string s in RowFields)
dt.Columns.Add(s);
foreach (var col in ColList)
dt.Columns.Add(col.Name.ToString()); // Cretes the result columns.//
foreach (var RowName in RowList)
{
DataRow row = dt.NewRow();
string strFilter = string.Empty;
foreach (string Field in RowFields)
{
row[Field] = RowName[Field];
strFilter += " and " + Field + " = '" + RowName[Field].ToString() + "'";
}
strFilter = strFilter.Substring(5);
foreach (var col in ColList)
{
string filter = strFilter;
string[] strColValues = col.Name.ToString().Split(Separator.ToCharArray(), StringSplitOptions.None);
for (int i = 0; i < ColumnFields.Length; i++)
filter += " and " + ColumnFields[i] + " = '" + strColValues[i] + "'";
row[col.Name.ToString()] = GetData(filter, DataField, Aggregate);
}
dt.Rows.Add(row);
}
return dt;
}
public DataTable PivotAllocationData(string DataField, AggregateFunction Aggregate, string[] RowFields, string[] ColumnFields)
{
DataTable dt = new DataTable();
string Separator = ".";
var RowList = _SourceTable.DefaultView.ToTable(true, RowFields).AsEnumerable().ToList();
for (int index = RowFields.Count() - 1; index >= 0; index--)
RowList = RowList.OrderBy(x => x.Field<object>(RowFields[index])).ToList();
// Gets the list of columns .(dot) separated.
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(RowFields);
foreach (string s in RowFields)
dt.Columns.Add(s);
foreach (var col in ColList)
dt.Columns.Add(col.Name.ToString()); // Cretes the result columns.//
foreach (var RowName in RowList)
{
DataRow row = dt.NewRow();
string strFilter = string.Empty;
foreach (string Field in RowFields)
{
row[Field] = RowName[Field];
strFilter += " and " + Field + " = '" + RowName[Field].ToString() + "'";
}
strFilter = strFilter.Substring(5);
foreach (var col in ColList)
{
string filter = strFilter;
string[] strColValues = col.Name.ToString().Split(Separator.ToCharArray(), StringSplitOptions.None);
for (int i = 0; i < ColumnFields.Length; i++)
filter += " and " + ColumnFields[i] + " = '" + strColValues[i] + "'";
row[col.Name.ToString()] = GetAllocationData(filter, DataField, Aggregate);
}
dt.Rows.Add(row);
}
return dt;
}
/// <summary>
/// Retrives the data for matching RowField value and ColumnFields values with Aggregate function applied on them.
/// </summary>
/// <param name="Filter">DataTable Filter condition as a string</param>
/// <param name="DataField">The column name which needs to spread out in Data Part of the Pivoted table</param>
/// <param name="Aggregate">Enumeration to determine which function to apply to aggregate the data</param>
/// <returns></returns>
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";
}
}
/// <summary>
/// Retrives the data for matching RowField value and ColumnFields values with Aggregate function applied on them.
/// </summary>
/// <param name="Filter">DataTable Filter condition as a string</param>
/// <param name="DataField">The column name which needs to spread out in Data Part of the Pivoted table</param>
/// <param name="Aggregate">Enumeration to determine which function to apply to aggregate the data</param>
/// <returns></returns>
private object GetAllocationData(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 GetAllocationSum(objList);
default:
return null;
}
}
catch (Exception ex)
{
return "#Error";
}
}
private object GetAverage(object[] objList)
{
return objList.Count() == 0 ? null : (object)(Convert.ToDecimal(GetSum(objList)) / objList.Count());
}
private object GetSum(object[] objList)
{
return objList.Count() == 0 ? null : (object)(objList.Aggregate(new decimal(), (x, y) => x += Convert.ToDecimal(y)) + "%");
}
private object GetAllocationSum(object[] objList)
{
return objList.Count() == 0 ? null : (object)(objList.Aggregate(new decimal(), (x, y) => x += Convert.ToDecimal(y)));
}
private object GetFirst(object[] objList)
{
return (objList.Count() == 0) ? null : objList.First();
}
private object GetLast(object[] objList)
{
return (objList.Count() == 0) ? null : objList.Last();
}
private object GetMax(object[] objList)
{
return (objList.Count() == 0) ? null : objList.Max();
}
private object GetMin(object[] objList)
{
return (objList.Count() == 0) ? null : objList.Min();
}
public enum AggregateFunction
{ カウント = 1、合計 = 2、最初 = 3、最後 = 4、平均 = 5、最大 = 6、最小 = 7、存在 = 8 }