public string GetDescription(DataSchema dataSchema) { var parts = new List <string>(); if (RowHeaders.Any()) { parts.Add(Resources.PivotSpec_GetDescription_Row_Headers_); parts.AddRange(RowHeaders.Select(header => header.Caption ?? header.SourceColumn.ToString())); } if (ColumnHeaders.Any()) { if (parts.Any()) { parts.Add(string.Empty); } parts.Add(Resources.PivotSpec_GetDescription_Column_Headers_); parts.AddRange(ColumnHeaders.Select(header => header.Caption ?? header.SourceColumn.ToString())); } if (Values.Any()) { if (parts.Any()) { parts.Add(string.Empty); } parts.Add(Resources.PivotSpec_GetDescription_Values_); parts.AddRange(Values.Select(value => (ColumnCaption.ExplicitCaption(value.Caption) ?? value.AggregateOperation.QualifyColumnCaption(value.SourceColumn.ToColumnCaption())) .GetCaption(dataSchema.DataSchemaLocalizer))); } return(string.Join(Environment.NewLine, parts)); }
public IEnumerable <RowItem> GroupAndTotal(IEnumerable <RowItem> rows, IList <DataPropertyDescriptor> propertyDescriptors) { var rowsByRowHeader = rows.ToLookup(row => { CancellationToken.ThrowIfCancellationRequested(); return(ImmutableList.ValueOf(RowHeaders.Select(tuple => tuple.Item1.GetValue(row)))); }); propertyDescriptors.AddRange(RowHeaders.Select((tuple, index) => new IndexedPropertyDescriptor(DataSchema, index, tuple.Item1, tuple.Item2))); var columnHeaders = new Dictionary <ImmutableList <object>, int>(); var resultRows = new List <RowItem>(); List <List <object> > aggregateValues = new List <List <object> >(); foreach (IGrouping <ImmutableList <object>, RowItem> rowGroup in rowsByRowHeader) { foreach (var list in aggregateValues) { list.Clear(); } var rowValues = rowGroup.Key.ToList(); foreach (RowItem row in rowGroup) { // ReSharper disable AccessToForEachVariableInClosure var columnHeader = ImmutableList.ValueOf(ColumnHeaders.Select(pd => pd.GetValue(row))); // ReSharper restore AccessToForEachVariableInClosure int columnHeaderIndex; if (!columnHeaders.TryGetValue(columnHeader, out columnHeaderIndex)) { columnHeaderIndex = columnHeaders.Count; columnHeaders.Add(columnHeader, columnHeaderIndex); foreach (var aggregateColumn in AggregateColumns) { propertyDescriptors.Add(MakePropertyDescriptor(propertyDescriptors.Count, columnHeader, aggregateColumn.Item1, aggregateColumn.Item2, aggregateColumn.Item3)); aggregateValues.Add(new List <object>()); } } for (int iAggColumn = 0; iAggColumn < AggregateColumns.Count; iAggColumn++) { var value = AggregateColumns[iAggColumn].Item1.GetValue(row); if (value != null) { var aggList = aggregateValues[iAggColumn + columnHeaderIndex * AggregateColumns.Count]; aggList.Add(value); } } } for (int iGroup = 0; iGroup < columnHeaders.Count; iGroup++) { for (int iAggColumn = 0; iAggColumn < AggregateColumns.Count; iAggColumn++) { int aggregateValueIndex = iGroup * AggregateColumns.Count + iAggColumn; var individualValues = aggregateValues[aggregateValueIndex]; if (individualValues.Count == 0) { rowValues.Add(null); } else { rowValues.Add(AggregateColumns[iAggColumn].Item3.CalculateValue(DataSchema, individualValues)); } } } resultRows.Add(new RowItem(rowValues)); } return(resultRows); }