【问题标题】:An exception of type 'System.OutOfMemoryException' occurred in itextsharp.dll but was not handled in user codeitextsharp.dll 中出现“System.OutOfMemoryException”类型的异常,但未在用户代码中处理
【发布时间】:2026-02-09 16:05:01
【问题描述】:

我正在使用 iTextSharp 创建 pdf。我有 10 万条记录,但出现以下异常:

“System.OutOfMemoryException”类型的异常发生在 itextsharp.dll 但未在用户代码中处理 在该行: bodyTable.AddCell(currentProperty.GetValue(lst, null).ToString());

代码是:

var doc = new Document(pageSize);

PdfWriter.GetInstance(doc, stream);
doc.Open();

//Get exportable count
int columns = 0;

Type currentType = list[0].GetType();

//PREPARE HEADER
//foreach visible columns check if current object has proerpty
//else search in inner properties
foreach (var visibleColumn in visibleColumns)
{
    if (currentType.GetProperties().FirstOrDefault(p => p.Name == visibleColumn.Key) != null)
    {
        columns++;
    }
    else
    {
        //check child property objects
        var childProperties = currentType.GetProperties();
        foreach (var prop in childProperties)
        {
            if (prop.PropertyType.BaseType == typeof(BaseEntity))
            {
                if (prop.PropertyType.GetProperties().FirstOrDefault(p => p.Name == visibleColumn.Key) != null)
                {
                    columns++;
                    break;
                }
            }
        }
    }
}


//header
var headerTable = new PdfPTable(columns);
headerTable.WidthPercentage = 100f;

foreach (var visibleColumn in visibleColumns)
{
    if (currentType.GetProperties().FirstOrDefault(p => p.Name == visibleColumn.Key) != null)
    {
        //headerTable.AddCell(prop.Name);
        headerTable.AddCell(visibleColumn.Value);
    }
    else
    {
        //check child property objects
        var childProperties = currentType.GetProperties();
        foreach (var prop in childProperties)
        {
            if (prop.PropertyType.BaseType == typeof(BaseEntity))
            {
                if (prop.PropertyType.GetProperties().FirstOrDefault(p => p.Name == visibleColumn.Key) != null)
                {
                    //headerTable.AddCell(prop.Name);
                    headerTable.AddCell(visibleColumn.Value);
                    break;
                }
            }
        }
    }
}

doc.Add(headerTable);

var bodyTable = new PdfPTable(columns);
bodyTable.Complete = false;
bodyTable.WidthPercentage = 100f;

//PREPARE DATA
foreach (var lst in list)
{
    int col = 1;
    foreach (var visibleColumn in visibleColumns)
    {
        var currentProperty = currentType.GetProperties().FirstOrDefault(p => p.Name == visibleColumn.Key);
        if (currentProperty != null)
        {
            if (currentProperty.GetValue(lst, null) != null)
                bodyTable.AddCell(currentProperty.GetValue(lst, null).ToString());
            else
                bodyTable.AddCell(string.Empty);

            col++;
        }
        else
        {
            //check child property objects
            var childProperties = currentType.GetProperties().Where(p => p.PropertyType.BaseType == typeof(BaseEntity));
            foreach (var prop in childProperties)
            {
                currentProperty = prop.PropertyType.GetProperties().FirstOrDefault(p => p.Name == visibleColumn.Key);
                if (currentProperty != null)
                {
                    var currentPropertyObjectValue = prop.GetValue(lst, null);
                    if (currentPropertyObjectValue != null)
                    {
                        bodyTable.AddCell(currentProperty.GetValue(currentPropertyObjectValue, null).ToString());
                    }
                    else
                    {
                        bodyTable.AddCell(string.Empty);
                    }
                    break;
                }
            }
        }
    }
}

doc.Add(bodyTable);

doc.Close();

【问题讨论】:

  • 堆栈跟踪会很有用。此外,所涉及的数据的大小是多少。 10 万 == 10000 对吗?但是每条记录有多大?系统总共有多少内存?也许这是计算机内存不足的真实案例。
  • 十万 = 100000。表示 100000 行和 40 列。每个单元格包含大约 20 个字符数据。我的系统有 8 GB RAM。
  • 什么是十万?我以前从未听过这个词。

标签: asp.net-mvc pdf c#-4.0 itextsharp


【解决方案1】:

根据您为内存消耗提供的数据,对内存需求的粗略计算得出 100000 * 40 * (2*20+4) = 167MB。在您的内存限制范围内,但这只是一个下限。我想每个 Cell 对象都很大。如果每个单元格有 512 字节的开销,那么您可能会很好地看到 2GB 的占用空间。我认为它可能更多,因为 PDF 是一个复杂的野兽。

因此,您实际上可能会遇到内存不足的情况。如果不是您的计算机,那么至少 C# 已经为自己的事情留出了一点点。

我会先做一件事 - 检查内存消耗,例如 here。您甚至可以很好地尝试 10、100、1000、10000、100000 行,并查看程序运行的行数。

您也许可以尝试完全不同的事情。如果您尝试打印包含大量数据的格式良好的表格,也许您可​​以输出一个 HTML 文档,这可以增量完成,您只需将内容写入文件即可完成,而不是使用第三方库.然后,您可以将该 HTML 文档“打印”为 PDF。 * 到rescue 再次遇到这个问题。

【讨论】:

  • 它不是 Java 而是 .NET,因此您可能需要修改您的答案。
  • @AmedeeVanGasse 哎呀,这是一个有趣的错误。感谢您指出。我将建议更改为 C#。和以前一样,这不是一个解决方案,而是一些可能对 Sachin 有所帮助的调查途径。
最近更新 更多