.net 使用iText 7(8.0)测试PDF文件中是否存在字符串

brjng4g3  于 2023-11-20  发布在  .NET
关注(0)|答案(2)|浏览(238)

我目前正在做一些基本的基准测试(生成,拆分,合并,读取,压缩)来选择一个C# Pdf库在我的项目中使用。
我正在尝试从PDF文件中提取文本,并检查文本是否包含字符串。该文件是一个生成的发票,具有可利用的文本行,因此可以使用OCR,但不是必要的。
以DYNAMIC PDF为例,文档清晰

PdfDocument inputDocument = new PdfDocument(RessourcesBenchmark.PDF_MERGE_PAGE_TO_APPEND_PATH);
var text = inputDocument.GetText();

字符串
如何在C#中使用iText实现这一点?iText文档做得很奇怪,你要么阅读所有的API,要么阅读他们网站上的电子书或示例,这些总是非常具体的。我找到了this SO article关于注解的信息,并将PDF作为流阅读。
如果有人有一个例子或一个片段来指导我,我已经花了2个小时在这上面。
在我的基准测试之后,我会要求至少将代码发布到github,因为所有这些libraires文档并不总是显而易见的。

camsedfj

camsedfj1#

在André Lemos的帮助下,我找到了一个解决方案。我将在这里发布完整的实现。
在另一篇文章中,我们必须创建一个实现ITextExtractionStrategy接口的自定义类。也许iText中的抽象类可以省去这一步。

//To be able to extract text from our pdf document
    public class CustomTextExtractionStrategy : ITextExtractionStrategy
    {
        private string textResult { get; set; }

        public CustomTextExtractionStrategy()
        {
        }

        public void EventOccurred(IEventData data, EventType type)
        {
            if (type is EventType.RENDER_TEXT)
            {
                textResult += ((TextRenderInfo)data).GetText();
                
            }
        }

        public string GetResultantText()
        {
            return textResult ?? string.Empty;
        }

        public ICollection<EventType> GetSupportedEvents()
        {
            return new List<EventType>{
                EventType.BEGIN_TEXT,
                EventType.RENDER_TEXT,
                EventType.END_TEXT,
                //EventType.RENDER_IMAGE,
                EventType.RENDER_PATH,
                EventType.CLIP_PATH_CHANGED };
        }
    }

字符串
然后,我们可以将此类用作PdfCanvasProcessor中的参数来处理文本,并通过获取CASTED事件来处理

public class ITextBenchmark
{
    public ITextBenchmark()
    {
    }
    // Our text extracting method
    public IEnumerable<string> TextExtraction()
    {
        var pdftext = new StringBuilder();
        CustomTextExtractionStrategy customTextExtractionStrategy = new CustomTextExtractionStrategy();
        PdfDocument pdfDocument = new PdfDocument(new PdfReader(RessourcesBenchmark.PDF_MERGE_PAGE_TO_APPEND_PATH));
        PdfCanvasProcessor parser = new PdfCanvasProcessor(customTextExtractionStrategy);

        //Process all the pages of the document
        for (int i = 1; i <= pdfDocument.GetNumberOfPages(); i++)
        {
            parser.ProcessPageContent(pdfDocument.GetPage(i));

            // Here we have to extract data from the event listener contained in the parser. 
            var eventResult = (CustomTextExtractionStrategy)parser.GetEventListener();
            pdftext.Append(eventResult.GetResultantText());
            parser.Reset();
        }

        if (pdftext.ToString().Contains("*"))
        {
            return new List<string> { $"The pdf contains '*'" };
        }
        else
        {
            return new List<string> { "Unavailable" };
        }
    }
}

odopli94

odopli942#

有一种方法可以使用C# * 从PDF中检索文本,而不需要 * 使用自定义文本提取策略。使用NET Core很简单,只需要itext7 nuget包。(可以在here中找到工作解决方案的链接)。

using iText.Kernel.Pdf;
using iText.Kernel.Pdf.Canvas.Parser;
using iText.Kernel.Pdf.Canvas.Parser.Listener;

namespace ScanTextInPDFs
{
    internal class Program
    {
        public static async Task Main(string[] args)
        {
            string executingDirectory = AppContext.BaseDirectory;

            byte[] bytes = await File.ReadAllBytesAsync($"{executingDirectory}PDFs\\Brochure.pdf");
            string textToFind = "Lorem ipsum";
            bool foundText = false;

            using (MemoryStream memoryStream = new MemoryStream(bytes))
            {
                using PdfReader pdfReader = new PdfReader(memoryStream);
                using PdfDocument pdfDocument = new PdfDocument(pdfReader);

                for (int page = 1; page <= pdfDocument.GetNumberOfPages(); page++)
                {
                    PdfPage pdfPage = pdfDocument.GetPage(page);
                    string pageText = PdfTextExtractor.GetTextFromPage(pdfPage, new SimpleTextExtractionStrategy());

                    if (pageText.Contains(textToFind, StringComparison.Ordinal))
                        foundText = true;
                }
            }

            if (foundText)
                Console.WriteLine($"Found '{textToFind}' in the pdf.");
            else
                Console.WriteLine($"Did not find '{textToFind}' in the pdf.");
        }
    }
}

字符串

相关问题