Java Недостаточно памяти для чтения и записи в xlsx - PullRequest
0 голосов
/ 30 августа 2018

Мне нужно прочитать несколько файлов xlsx в поисках данных, относящихся к сотруднику, и одновременно создать еще один файл xlsx (если я найду данные в любом из файлов) с именем файла в качестве идентификатора сотрудника, добавленного к имени, в котором я нашел данные. Например. есть сотрудник с emp id 1, и есть несколько файлов xlsx, таких как A, B, C ... и т. д .; Мне нужно искать данные, относящиеся к emp id 1 в каждом файле, и для файлов, которые я получаю, мне нужно создать файл с именем 1_A.xlsx.

Теперь, хотя я создал логику и использую API-интерфейсы Apache POI для чтения и записи, мой код выдает ошибку Out Of Memory после создания только первого файла с данными. И не может прочитать остальные файлы. Я пытался использовать SXSSF вместо XSSF, но происходит то же OOM.

Увеличение пространства кучи не вариант для меня. Пожалуйста, помогите здесь ... Спасибо заранее.

Вот кусок кода:

//Reader:


 Row row = null;
   List<Row> listOfRecords = new ArrayList<Row>();
        try {
            FileInputStream fis = new FileInputStream(metaDataFile);
            new InputStreamReader(fis, "ISO-8859-1");
            XSSFWorkbook wb = new XSSFWorkbook(fis);
            XSSFSheet sheet = wb.getSheetAt(0);
            Iterator<Row> rowIterator = sheet.iterator();
            while (rowIterator.hasNext()) {
                row = rowIterator.next();
                if (!isEmptyRow(row)) {
                    listOfRecords.add(row);
                }
            }
            wb.close();
            fis.close();

//Writer
LOGGER.info("in createWorkbook " );
        Workbook empWorkbook = new SXSSFWorkbook(200);
        Sheet empSheet = empWorkbook.createSheet("Itype Sheet For Emp_"
                + personnelNumber);
        int rowNum = listOfRecords.size();
        System.out.println("Creating excel");
        Cell c = null;
        for (int i = 0; i < rowNum; i++) {

            Row record = listOfRecords.get(i);
            Row empRow = empSheet.createRow(i++);
            if (!isEmptyRow(record)) {
                int colNum = record.getLastCellNum() + 1;

                for (int j = 0; j < colNum; j++) {
                    Cell newCell = empRow.createCell(j);

                    System.out.println("cellVal:"
                            + String.valueOf(record.getCell(j)));
                    newCell.setCellValue(String.valueOf(record.getCell(j)));

                }
            }
        }

Метод писателя вызывается из читателя.

1 Ответ

0 голосов
/ 04 сентября 2018

Чтение нескольких файлов xlsx - дело непростое, но я наконец решил.

Мне пришлось несколько раз разбить мой код, чтобы понять, что ошибка OOM произошла из-за того, что после чтения 3 файлов не осталось больше памяти для обработки остальных файлов. xlsx файлы - это сжатые xml файлы. Поэтому, когда мы пытаемся прочитать их, используя API-интерфейсы XSSF или SXSSF, он загружает весь DOM в память, после чего его душит. Я нашел отличное решение здесь: [https://github.com/monitorjbl/excel-streaming-reader] Надеюсь, что это поможет другим, кто придет сюда, столкнувшись с той же проблемой.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...