У меня есть куча pdf-файлов (из разных источников), и я хотел бы извлечь из них текст (к сожалению, не могу прикрепить файлы).
Текущий результат синтаксического анализа :
- Tika молча возвращает текст, в котором отсутствует много необходимых данных.
- Использование PDFBox напрямую выдает кучу предупреждений (см. Ниже), а также удаляет данные, которые он не мог распознать
- Adobe Acrobat Reader (действие «Сохранить как текст») сохраняет исходную структуру документа, но вместо проблемных c шрифтов помещает «??????»
Все комбинированные предупреждения, которые я вижу до сих пор, из PDFBox:
Aug 06, 2020 3:10:49 PM org.apache.pdfbox.pdmodel.font.PDType0Font toUnicode
WARNING: No Unicode mapping for CID+51 (51) in font AUDQZE+OpenSans-Identity-H
Aug 06, 2020 3:10:49 PM org.apache.pdfbox.pdmodel.font.PDType0Font toUnicode
WARNING: No Unicode mapping for CID+5 (5) in font HCUDUN+DroidSerif-Identity-H
Aug 06, 2020 3:10:49 PM org.apache.pdfbox.pdmodel.font.PDType0Font toUnicode
WARNING: No Unicode mapping for CID+5 (5) in font AUDQZE+OpenSans-Identity-H
Aug 06, 2020 3:10:49 PM org.apache.pdfbox.pdmodel.font.PDType0Font toUnicode
WARNING: No Unicode mapping for CID+55 (55) in font GFEIIG+OpenSans
Aug 06, 2020 3:10:49 PM org.apache.pdfbox.pdmodel.font.PDType0Font toUnicode
WARNING: No Unicode mapping for CID+5 (5) in font GFEIIF+DroidSerif
Aug 06, 2020 3:10:50 PM org.apache.pdfbox.pdmodel.font.PDType0Font toUnicode
WARNING: No Unicode mapping for CID+5 (5) in font GFEIIG+OpenSans
В идеале я бы хотел использовать Tika, так как я ожидаю форматов Word и HTML.
Вопрос : Итак, мне было интересно, могу ли я попросить Tika (или PDFBox) использовать другое отображение кодировки, такое как ASCII, чтобы убедиться, что эти проблемные шрифты c могут быть проанализированы с помощью альтернативы таблице Unicode?
Вот Нашел следующее:
Почему я получаю gibberi sh (G38G43G36G51G5) при извлечении текста? Это связано с тем, что символы в документе PDF могут использовать пользовательскую кодировку вместо Unicode или ASCII. Когда вы видите текст gibberi sh, это, вероятно, означает, что используется бессмысленная внутренняя кодировка. Единственный способ получить доступ к тексту - использовать OCR. Это может быть улучшением в будущем.
^ Означает ли это, что нижележащий PDFBox уже проверяет кодировку ASCII для шрифта, и мне вообще не нужно беспокоиться об ASCII?
Тупой вопрос : Могу ли я каким-то образом предоставить недостающее отображение Unicode в PDFBox? Используете Тику? Скажем, у меня ограниченное количество известных сбоев сопоставлений Unicode, могу ли я каким-то образом передать такую информацию синтаксическому анализатору?
Мой случай : у меня уже есть куча документов (поэтому нет контроля над созданием) Я Я хотел бы выполнить поиск, поэтому я решил создать их индекс с помощью Tika. Я предполагаю, что большая часть файла pdf будет иметь проблему с не встроенным шрифтом. Так что потенциально я подумал об использовании свойства Tika Metadata.get(UNMAPPED_UNICODE_CHARS_PER_PAGE)
, чтобы решить, требуется ли им анализ OCR Tika (pdfConfig.setOcrStrategy(OCR_STRATEGY.OCR_ONLY)
) после анализа NO_OCR. OCR в 10 раз медленнее и менее точное (оно также считывает изображения, такие как lo go, и пытается понять его, хотя это не нужно и просто добавляет шум), но я не вижу других вариантов.
Оцените любые мысли по этому поводу, спасибо.
UPD
Спасибо @mkl за указание на введение отображения шрифтов перед синтаксическим анализом. Интересно, можно ли автоматизировать это, если у меня есть шрифты (файлы TTF), с помощью которых был создан PDF-файл?
Фрагменты кода, которые я использую для синтаксического анализа, если это поможет:
Tika:
static void parseAndPrint(String fileName) throws IOException, TikaException {
Tika tika = new Tika();
InputStream is = Main.class.getResourceAsStream(fileName);
System.out.println(tika.parseToString(is));
}
PDFBox:
static void parseAndPrint(String fileName) throws IOException {
System.out.println("========= Start File: " + fileName);
InputStream file = Main.class.getResourceAsStream(fileName);
PDFTextStripper tStripper = new PDFTextStripper();
PDDocument document = PDDocument.load(file);
System.out.print(tStripper.getText(document));
document.close();
System.out.println("========= End File: " + fileName);
}