Open XML SDK Pivots - 如何推迟 PivotCacheRecords 的枚举?

发布于 2024-12-13 12:35:04 字数 1449 浏览 2 评论 0原文

我正在尝试合并多个不包含数据源的 Excel 工作簿。由于我无法控制的原因,我无法访问驾驶数据。

每个工作簿始终只包含一个数据透视表,并且它们可靠地共享某些字段。理想情况下,用户可以选择一组字段和工作簿列表,并获得包含所有组合数据的一个工作簿。我并没有忘记这不是正确的做事方式,但这就是我所面对的。

问题;

当我寻址 PivotTableCacheRecordsPart 的 PivotCacheRecords 属性的任何成员时,它会立即将整个列表枚举到内存中。由于某些工作表具有数万行和 50 多列,这会很快耗尽所有可用内存。这是一个示例片段。

  var pivotDefs = spredDoc.WorkbookPart.PivotTableCacheDefinitionParts.First();

  ...

  int i = 0;      
  var records = pivotDefs.PivotTableCacheRecordsPart.PivotCacheRecords;

  foreach(var record in records)
  {
    var fields = record.ToList();
    lastUsedRow++;
    for (int j = 0; j < fieldCount; j++)
    {
      if (reportToDefColumnLookup.ContainsKey(j) && !(fields[j] is MissingItem))
      {
        var readValue = fields[j].GetAttribute("v", "").Value;
        writer.Write(readValue + "\t");
      }
      else
      {
        writer.Write("\t");
      }
    }
    writer.WriteLine();
    i++;
    if (i % 2000 == 0)
    {
      System.Diagnostics.Trace.WriteLine(string.Format("[Pivot Handler] {0} records read", i.ToString()));
    }                               
  }

当“记录”被处理时(在本例中,当 foreach 逻辑调用其枚举器时 - 但您可以通过调用任何成员属性/函数来复制该行为),整个列表将被加载到内存中。理想的解决方案是读取每条记录并在读取后将其卸载。我尝试从列表中删除该元素,但似乎没有任何效果。

我对以某种方式合并两个主元定义而不复制表格数据有一个非常模糊的想法,但我不知道如何去做。

我没有可用的预算。任何图书馆建议都必须是免费的。我探索过 EPPlus,但它没有很好的数据透视表支持。

任何人都可以阐明这一点或为我指出一个可能的方向吗?众所周知,开放 XML 文档很难找到,而且最多也很神秘。

提前致谢。

I am trying to combine multiple excel workbooks which do not have the data source included in them. For reasons far beyond my control, I have no means to access the driving data.

Each workbook always contains exactly one pivot table, and they reliably share certain fields. Ideally, a user can choose a group of fields, and a list of workbooks, and would get one workbook with all of the combined data. It is not lost on me that is not the right way to do things, but its the hand I was dealt.

The problem;

When I address the any member of the PivotCacheRecords property of PivotTableCacheRecordsPart, it instantly enumerates the entire list into memory. Due to certain sheets having tens of thousands of rows, and 50+ columns, this quickly consumes all available memory. Here is an example snippit.

  var pivotDefs = spredDoc.WorkbookPart.PivotTableCacheDefinitionParts.First();

  ...

  int i = 0;      
  var records = pivotDefs.PivotTableCacheRecordsPart.PivotCacheRecords;

  foreach(var record in records)
  {
    var fields = record.ToList();
    lastUsedRow++;
    for (int j = 0; j < fieldCount; j++)
    {
      if (reportToDefColumnLookup.ContainsKey(j) && !(fields[j] is MissingItem))
      {
        var readValue = fields[j].GetAttribute("v", "").Value;
        writer.Write(readValue + "\t");
      }
      else
      {
        writer.Write("\t");
      }
    }
    writer.WriteLine();
    i++;
    if (i % 2000 == 0)
    {
      System.Diagnostics.Trace.WriteLine(string.Format("[Pivot Handler] {0} records read", i.ToString()));
    }                               
  }

The moment "records" is addressed (in this case, when the foreach logic calls for its enumerator - but you could replicate the behavior by calling any member property/function) the entire list is loaded into memory. The ideal solution would read each record and unload it after reading it. I tried removing the element from the list, but it did not seem to have any effect.

I have an extremely vague idea about somehow merging two pivot definitions without reproducing the tabular data, but I have no idea how to go about doing that.

I do not have a budget available for this. Any library suggestions would have to be free. I have explored EPPlus, but it does not have very good PivotTable support.

Could any one shed light on this or point me in a possible direction? Open XML documentation is notoriously difficult to find and tends to be cryptic at best.

Thanks in advance.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文