Converter PDF em texto é um problema difícil
(marginalia.nu)- Embora a indexação de PDFs tenha sido adicionada ao mecanismo de busca, obter de um PDF texto estruturado útil para pesquisa é muito mais complicado do que processar HTML
- O PDF é mais próximo de um formato gráfico baseado em coordenadas do que de um documento de texto, então glifos podem ser posicionados rotacionados, sobrepostos ou em ordem embaralhada
- O PDFTextStripper do PDFBox pode servir como ponto de partida, mas não preserva suficientemente estruturas semânticas como títulos e parágrafos, o que limita a avaliação de relevância na busca
- Para distinguir títulos e parágrafos, heurísticas como estatísticas de tamanho de fonte por página e mediana do espaçamento entre linhas são mais úteis do que critérios baseados no documento inteiro
- Como a extração perfeita de texto de PDF é difícil, um método bom o bastante que obtenha de forma estável a estrutura de título, resumo e corpo é uma meta realista para mecanismos de busca
Problemas revelados ao adicionar indexação de PDFs
- O mecanismo de busca passou recentemente a conseguir indexar o formato de arquivo PDF, e as mudanças serão distribuídas ao longo de alguns meses
- Do ponto de vista de um mecanismo de busca, um HTML limpo é o mais fácil de lidar, mas PDFs não oferecem de imediato o mesmo nível de texto estruturado
- Mesmo que o texto apareça visualmente, reconstruir frases e parágrafos pesquisáveis dentro de um PDF é praticamente um problema à parte
Por que PDFs dificultam a extração de texto
- PDF não é um formato de texto comum; ele é mais próximo de um formato gráfico
- Sua representação interna se parece mais com a colocação de glifos em coordenadas sobre um “papel” do que com frases ou parágrafos
- Os glifos podem estar nas seguintes condições
- Rotacionados
- Sobrepostos uns aos outros
- Aparecendo em uma ordem diferente da ordem de leitura
- Com pouquíssima informação semântica associada
- O simples fato de a busca com
ctrl+ffuncionar em visualizadores de PDF ou navegadores já é um resultado bastante surpreendente - Modelos de aprendizado de máquina baseados em visão podem ser uma boa abordagem no momento, mas não se adequam à escala de processar centenas de GB de PDFs em um único servidor sem GPU
É possível começar com PDFBox, mas não é suficiente
- Como o problema não é totalmente inexplorado, a classe PDFTextStripper do PDFBox pode ser usada como ponto de partida
- O PDFTextStripper extrai texto de PDFs, mas, como o nome sugere, seu foco é “arrancar” o texto
- Para um mecanismo de busca, informações semânticas como títulos são sinais importantes de relevância, mas é difícil obter estrutura suficiente apenas com o resultado básico da extração
Heurísticas para encontrar títulos
- A detecção de títulos mais simples consiste em procurar linhas em semibold ou mais grossas separadas de outros textos
- Mas nem todos os títulos são exibidos em negrito, e muitos documentos diferenciam títulos pelo tamanho da fonte
- Um ponto de referência global de tamanho de fonte varia de documento para documento
- Um documento pode usar corpo em 10 pt e títulos em 16 pt
- Outro documento pode usar corpo em 14 pt e títulos em 20 pt
- Estatísticas por página às vezes são mais adequadas do que as do documento inteiro
- A primeira página pode ter uma escolha de fontes muito diferente do restante por causa do resumo e da lista de autores
- No documento de exemplo, uma fonte de tamanho 17 é usada no título do documento, e fontes de tamanho 14 são usadas nos títulos seguintes
- Cada página geralmente tem um tamanho de fonte dominante correspondente ao corpo do texto
- Aplicar um fator de cerca de 20% à mediana do tamanho de fonte por página permite identificar títulos com razoável estabilidade
- Ainda há exceções, mas a maioria dos casos importantes pode ser capturada
Unir títulos de várias linhas em um só
- Títulos frequentemente são divididos em várias linhas por causa do estilo, então às vezes é necessário juntar linhas de título consecutivas em uma só
- O critério para decidir quando juntar não é simples
- No exemplo, as seguintes condições aparecem juntas
- Título de duas linhas
- Título alinhado à direita
- Nomes de autores em semibold logo após o título
- Um título sem negrito algumas linhas abaixo
- Como a indentação também é usada como sinal de separação de parágrafos, títulos alinhados à direita dificultam ainda mais a decisão
- Juntar títulos consecutivos que tenham o mesmo tamanho e peso de fonte geralmente funciona bem, mas também pode gerar resultados indesejados
Armadilhas criadas pelo espaçamento entre linhas na identificação de parágrafos
- O PDFTextStripper faz identificação de parágrafos razoavelmente bem
- Ele observa o espaçamento entre linhas e a indentação em conjunto para decidir onde separar parágrafos
- Há espaço para melhorias, especialmente na lógica de espaçamento entre linhas
- O grande problema do PDFTextStripper é usar um ponto de referência fixo para separar linhas
- Se o espaçamento entre linhas for maior que o ponto de referência, ele decide que não pertence ao mesmo parágrafo
- Isso não reflete suficientemente o fato de que cada documento tem espaçamentos diferentes
- Em rascunhos acadêmicos e preprints, espaçamento de 1,5 a 2 vezes é bastante comum
- Se o valor de referência for definido alto demais, alguns títulos podem ser absorvidos por parágrafos do corpo do texto, prejudicando a identificação de títulos
Ajuste com estatísticas de espaçamento entre linhas
- De forma semelhante ao tratamento do tamanho de fonte, é possível aplicar técnicas estatísticas à distância entre linhas
- Ao criar um histograma das distâncias entre linhas em uma página de texto, tende a aparecer um grande outlier
- A média é facilmente afetada por outliers, mas a mediana às vezes corresponde exatamente ao espaçamento usado no corpo do texto
- Ao aplicar um certo fator à mediana, é possível criar uma heurística de separação de parágrafos que resiste a diferentes espaçamentos entre linhas
A meta realista é estabilidade, não perfeição
- A extração de texto de PDFs dificilmente será perfeita
- O próprio formato PDF não foi projetado para esse tipo de tarefa, e surgem vários trade-offs ao escolher uma solução “boa o bastante”
- Um mecanismo de busca se interessa especialmente pelas seguintes informações
- Sinais de relevância como títulos
- Identificação do resumo
- Uma estrutura razoavelmente consistente do restante do texto
- Com esses objetivos, é possível chegar a uma solução que processe a maioria dos documentos relevantes sem grandes dificuldades
Textos de exemplo usados
Can Education be Standardized? Evidence from Kenya (2022) - Working PaperGuthrie Gray-Lobe, Anthony Keats, Michael Kremer, Isaac Mbiti, Owen W. OzierThe theory of ideas and Plato’s philosophy of mathematics (2019)Dembiński, B.The role of phronesis in Knowledge-Based Economy (2024)Anna Ceglarska, Cymbranowicz Katarzyna
1 comentários
Comentários do Hacker News
Às vezes acontece de eu ter me aprofundado em algo por meses ou anos, chegando a um nível de especialista, esquecer completamente disso e, mais tarde, pensar “isso é novo e interessante”
Mesmo tendo feito bastante coisa interessante, ela some da memória, e até que algo sirva de gatilho, sinto como se estivesse recomeçando a vida
Tenho uma vaga lembrança de ter feito algo bem legal com PDF e OCR uns 6 ou 7 anos atrás e, procurando, acho que era Tesseract
Era um hack mais próximo de uma heurística, e acho que a API antiga do Poppler na época não representava sequências de texto de uma forma adequada para APIs de acessibilidade
A seleção em múltiplas colunas entrou em alguma medida, mas depois foi difícil convencer os mantenedores sobre propostas de melhoria de desempenho, porque a heurística era um pouco diferente e, em algumas situações, mudava o resultado da seleção
Para começo de conversa, não fazia sentido exigir resultados idênticos quando não havia uma única “resposta correta”, e foi assim que a seleção em múltiplas colunas do kpdf surgiu em certa medida
Hoje em dia, é bem possível que faça mais sentido usar o Tesseract diretamente para esse tipo de finalidade
Não sei quando essa loucura vai acabar
A precisão padrão é maior, há aceleração por GPU, e ele implementa estruturas de modelos de detecção e reconhecimento de texto em um pipeline combinável
Também dá para treinar e fazer fine-tuning com PyTorch ou TensorFlow para melhorar ainda mais o desempenho em domínios específicos
Então esse tipo de coisa realmente acontece
O próximo trabalho é em uma área completamente diferente, então começo de novo pelo básico
Seria ótimo se alguém criasse algo como ferramentas de desenvolvedor de navegador para PDFs
Como em “inspecionar elemento”, seria bom ver o fluxo de conteúdo do PDF como fonte e verificar como operadores de texto
BT … ETou operadores de posicionamento de textoTjespecificam e geram cada pixelÉ o oposto da tendência atual de modelos visuais “olharem” para PDFs e lê-los como pessoas, mas seria muito melhor conseguir entender o que de fato existe dentro do arquivo PDF
Existem algumas ferramentas para inspecionar conteúdo de PDFs (https://news.ycombinator.com/item?id=41379101), mas elas param no nível de objetos do PDF, então o fluxo de conteúdo inteiro aparece apenas como um único objeto
Por exemplo, na página 8 do PDF, página 6 do documento mencionado no texto, em https://bfi.uchicago.edu/wp-content/uploads/2022/06/BFI_WP_2..., o texto é posicionado com operadores como
BT, configuração de fonte,TdeTJSe fosse possível ver essa “fonte” e o PDF renderizado lado a lado, e ao passar o mouse em um lado destacar a região correspondente no outro, daria para depurar como uma página HTML
Por exemplo, cada
Tjprovavelmente viraria um elemento DOM, eTJviraria um agrupamento de vários elementosComo isso precisa refletir corretamente o documento original para funcionar, é provável que a conversão seja bastante fiel
Você pode criar um JSON com
cpdf -output-json -output-json-parse-content-streams in.pdf -o out.jsone, depois de mexer nesse JSON, convertê-lo de volta para PDF comcpdf -j out.json -o out.pdfMas não há integração bidirecional em tempo real
Só que o modo de inspeção era navegando pela árvore de conteúdo, não inspecionando a página, e ele destacava os objetos na página
Não chegava ao nível de comandos; só ia até o nível de objetos ou fluxos
https://observablehq.com/@player1537/pdf-utilities
A direção não é apenas “olhar” para o PDF como uma pessoa e ler só o texto, mas entender o conteúdo, incluindo tabelas, imagens, texto, fórmulas e escrita à mão
Assim, ela faz parsing do PDF e roda vários modelos para extrair trechos em Markdown ou JSON, permitindo colocar os dados reais em agentes de IA, LLMs e outros aplicativos
https://tensorlake.ai
“PDF para texto” é uma expressão simplificada demais
Dentro dessa categoria há 1) OCR confiável para índices de busca ou entrada em bancos vetoriais, 2) extração de dados estruturados para obter valores específicos, 3) pipelines de documentos de ponta a ponta, como automação de pedidos de hipoteca
O que a Marginalia precisa resolver é o OCR do item 1, e isso está se tornando rapidamente uma commodity graças a modelos como o Gemini Flash
Vi várias empresas substituindo pipelines de OCR existentes pelo Flash e reduzindo bastante os custos, o que foi bem surpreendente
Mas os itens 2 e 3 são muito mais difíceis, e ainda há uma grande distância entre a saída bruta de OCR e pipelines de documentos de missão crítica em ambiente de produção
LLMs e modelos de visão-linguagem não são mágica, e quem espera 100% de automação vai se surpreender
Ainda são necessários construção e rotulagem de datasets, orquestração do pipeline
classificação -> segmentação -> extração, detecção de incerteza e revisão humana, ajuste fino etc.No longo prazo, pode chegar perto de uma automação quase completa, mas isso exige tempo e esforço; parece claro que o futuro caminha nessa direção
Relacionado a isso, comecei uma empresa de processamento de documentos com LLM chamada https://extend.ai
Fluxos de trabalho de negócios muitas vezes lidam só com alguns documentos predefinidos, mas um leitor de PDF genérico não sabe que documento o usuário vai abrir
É preciso reconhecer não só texto, mas também tabelas, cabeçalhos e rodapés, notas de rodapé, títulos, fórmulas matemáticas etc.
Como é para consumo humano, os erros precisam ser minimizados; portanto, não se deve usar OCR quando não for necessário, e é preciso aproveitar o texto básico embutido no PDF ao mesmo tempo em que se extrai a estrutura semântica
No fim, são necessários dois caminhos: um para PDFs que são apenas imagens e outro para PDFs dos quais se pode obter informação a partir do fluxo de conteúdo
Só que o fluxo de conteúdo pode conter texto diferente do que aparece de fato na tela. Há casos como informações escondidas em letras brancas ou implementações no estilo LaTeX que desenham acentos por comandos em vez de usar acentos Unicode
Normalmente isso roda como app local em dispositivos fracos dos usuários, e é bem possível que não haja servidor nem modelo de assinatura, então também não dá para usar modelos de IA em nuvem
Usuários de software de acessibilidade podem ter dificuldade para imprimir e preencher à caneta, então é preciso lidar não só com formulários limpos de acordo com a especificação, mas também com formulários para impressão
Esse ainda é um problema em aberto que não está nem perto de ser resolvido, e as soluções atuais são todas insuficientes de algum modo; não há uma solução única que resolva adequadamente todos os 5 pontos acima
Eles rotulam imagens muito bem e são aceitáveis para documentos simples, como texto em coluna única, título centralizado de uma única etapa, ou uma imagem ou tabela por página
A maioria das demos de MVP mostra exemplos desse tipo
Mas, em documentos complexos com tabelas e imagens misturadas, parece que ainda seriam necessários muito mais parâmetros só para chegar a um “nível ruim”
Hoje as alucinações são tão graves que até uma tabela simples, com título em cima, dados no centro e resumo embaixo, é difícil de usar diretamente
O OCR hoje é excelente, mas manter a estrutura global do documento é muito mais complicado
Obter HTML consistente em documentos grandes ainda parece distante; já Markdown dá resultados razoáveis ao passar várias vezes por um LLM para extrair a estrutura do documento e depois usá-la como contexto na extração página a página
Na Apple, esse problema foi tratado com bastante sucesso por vários anos, e o principal segredo era considerar tudo como geometria e tentar distinguir espaçamento entre palavras e espaçamento entre letras por análise de agrupamento
Em muitos PDFs isso funciona muito bem, mas há tantos tipos de PDF que sempre existem casos em que o resultado é ruim
Se eu fosse refazer isso hoje, manteria a geometria e evitaria OCR completamente, mas usaria aprendizado de máquina
A grande vantagem do aprendizado de máquina é que é possível automatizar totalmente a etapa de treinamento usando ferramentas existentes que geram PDFs a partir de textos conhecidos
Cena em que Bertrand Serlet apresentou esse recurso na WWDC 2009: https://youtu.be/FTfChHwGFf0?si=wNCfI9wZj1aj9rY7&t=308
Uma solução melhor é embutir no PDF o documento original editável junto com ele
No LibreOffice isso é fácil de fazer e, como comprime bem, normalmente quase não ocupa espaço
Assim é possível obter informações muito melhores sobre o texto e a semântica, e ainda funciona bem nos leitores de PDF existentes
Na área de descoberta eletrônica de provas, é comum que a parte que fornece evidências as despeje deliberadamente em PDF para dificultar o consumo do conteúdo pelos advogados da outra parte
Se os dois lados tiverem muito dinheiro, isso não é uma barreira; mas, por exemplo, um defensor público não tem recursos para contratar alguém que processe PDFs para um formato fácil de ler, então o tempo de processamento aumenta muito e o réu sofre uma carga psicológica maior
Talvez nem consigam processar os dados corretamente
A solução é tornar esse tipo de prática ilegal
Por exemplo, dados de interceptação telefônica deveriam ser fornecidos em um formato legível por máquina padronizado, e não há motivo ético para que simples atritos técnicos influenciem o resultado de processos criminais
Fico me perguntando quanto tempo levaria até essa solução surtir efeito
Na empresa também temos milhares desses arquivos; alguns são digitalizações péssimas, alguns têm OCR da Adobe embutido, mas a maioria não tem nada
Mas, em geral, não se tem esse controle
O PDF abaixo, na verdade, é um arquivo
.txtSe for salvo com a extensão
.pdf, ele pode ser aberto em um visualizador de PDF e também editado em um editor de textoPor exemplo, ao editar esse arquivo de texto, dá para alterar o texto exibido na tela quando o PDF é aberto, a fonte, o tamanho da letra, o espaçamento entre linhas, o número máximo de caracteres por linha, o número de linhas por página, a largura e a altura do papel, e até a orientação retrato/paisagem
O exemplo é uma estrutura mínima de PDF que começa com
%PDF-1.4, em queCatalog,Pages,Font,Page,Contents,xref,traileretc. são escritos diretamente como textoPDF não foi feito para texto, mas para layout e gráficos
O exemplo é bom, mas cada linha também pode ser quebrada em uma chamada por caractere, uma chamada por palavra, e a ordem pode ficar embaralhada
A seção “2.3.2 Portability” do documento de referência do PDF 1.0 descreve arquivos PDF como arquivos ASCII de 7 bits, afirmando que até documentos com imagens e caracteres especiais são descritos usando apenas o subconjunto imprimível de ASCII
Como resultado, ele explica que isso os torna altamente portáveis entre diferentes ambientes de hardware e sistemas operacionais
https://opensource.adobe.com/dc-acrobat-sdk-docs/pdfstandard...
Hoje em dia, a maioria dos PDFs tem todos os objetos comprimidos com deflate
Além disso, para dificultar ainda mais o rastreamento, muitos PDFs agrupam a maior parte dos objetos dentro de objetos do tipo stream de objetos e depois comprimem tudo de novo
Por isso, mesmo tentando rastrear o fim de
6 0 R, não dá para procurar6 0 Objem um editor de textoTenho um documento de que gosto e que mostra as dificuldades descritas neste texto: https://academic.oup.com/auk/article/126/4/717/5148354
Logo na primeira página há o texto típico em duas colunas, um título centralizado e uma caixa de texto encaixada entre as duas colunas que altera o comprimento das linhas e a indentação
Depois aparecem cabeçalhos que mudam entre páginas ímpares e pares, além de regras de cabeçalho de seção que variam bastante
Para piorar, não há espaçamento extra entre parágrafos e nem sempre existe indentação na primeira linha, então ele reúne todo tipo de dificuldade
Em cerca de 95% dos casos isso era bem razoável, e por muitos anos bastou para o PDFKit e o Preview do Mac
Se pensarmos no aplicativo original que gerou o PDF, por exemplo um processador de texto, é bem provável que ele tenha renderizado o texto a partir de seu próprio buffer de texto para o contexto PDF em uma ordem bastante razoável
Por isso, mesmo em documentos de duas colunas, muitas vezes o texto fluía corretamente da coluna da esquerda para a da direita, e já estava na ordem correta dentro do PDF
Porém, no caso de rodapés e cabeçalhos de página, não há como saber em que ordem o aplicativo gerador do PDF os despejou no contexto
Extrair texto de um PDF, até mesmo texto estruturado, não é nada fácil
Raspar uma tabela de um documento HTML costuma ser simples mesmo quando o site usa o antipadrão de transformar tudo em
div, e fica ainda mais fácil quando usa elementos semânticosCom PDF não é assim
Não sou especialista no formato, então não sei quanto suporte a estrutura semântica existe, mas já vi muitos PDFs que criam tabelas como uma coleção solta de elementos gráficos e de texto que só parecem uma tabela quando renderizados
Na prática, tive bastante sucesso extraindo dados de tabelas convertendo o PDF em HTML com os utilitários PDF do Poppler, depois procurando os cabeçalhos de tabela esperados e calculando as colunas pela coordenada x de cada valor para extrair os valores por linha
É uma abordagem suja, mas funcionou de forma estável para o que eu precisava, e foi muito melhor do que lidar com texto comum formatado em que o espaçamento varia ou há quebras de linha no meio das linhas
Ela também tem várias outras funcionalidades, mas o objetivo principal é permitir interagir de uma forma mais humana, como em
page.find('text:bold:contains("Summary").below().extract_text()Como cada PDF é um pesadelo sob medida, estou reunindo exemplos difíceis de extração para usá-los como base de uma biblioteca de metodologias
https://jsoma.github.io/natural-pdf/
https://badpdfs.com/
Se alguém conhecer uma biblioteca de extração de tabelas de PDF que possa ser integrada a um app em C++ e seja gratuita ou custe menos de algumas centenas de dólares, gostaria de saber
Há inúmeras maneiras de criar o mesmo PDF
Algumas ferramentas estão mais próximas de exportar, a partir de um editor gráfico, um layout contendo texto e gráficos; outras estão mais próximas de exportar texto e gráficos com as palavras em primeiro lugar, como em um processador de texto
A perspectiva do aplicativo gerador sobre como lidar com as informações frequentemente influencia a forma como ele produz o PDF
Se você está procurando um utilitário pronto, ferramentas como cisdem já resolvem razoavelmente bem a extração de dados estruturados para usuários locais
Existem muitas ferramentas desse tipo, e muitas prometem suporte a dados estruturados, mas elas precisam se encaixar bem no trabalho que você quer fazer
PDF é um formato de apresentação
Ele é otimizado para os olhos humanos e para impressoras, e suas funcionalidades foram aumentando cada vez mais
Como meio de transmissão de dados entre máquinas, é péssimo, mas é muito bom para uma pessoa ler ou para armazenar uma página A4
Se você parte da premissa de que, como um
.pdfarmazena texto, é esse texto que você quer, é basicamente o mesmo que dizer para simplesmente aumentar seus olhosCaso contrário, é preciso lidar com algo extremamente complexo
Antes de tudo, já há a questão de saber se aquele texto é texto de verdade ou uma imagem
Os olhos humanos conseguem ler de qualquer jeito, bastando recolocar os óculos, mas um parser pode quebrar com erros de segmentação
Como o PDF é feito para leitura humana, para ler um PDF é preciso imitar uma pessoa
Há algum tempo fiz um parser de PDF de brinquedo e fiquei bem perplexo depois de entender como o formato funciona
Pensando nisso, é ainda mais estranho que PDFs sejam usados com tanta frequência em casos cheios de texto
Penso especialmente em faturas
Sistemas digitais deveriam conseguir extrair dados facilmente do arquivo e, ao mesmo tempo, o conteúdo deveria ser bem formatado para humanos
Acho que seria muito melhor se a indústria de tecnologia migrasse para um formato melhor