2
respostas

Qual a forma mais performática mais rápida para comparar arquivos muito grande

Olá galera,

Tenho dois arquivos textos, como notas fiscais, e há um código de nota por linha, esses arquivos tem mais de 2 mi de linhas. O problema é que um arquivo esta faltando algumas notas 4, e preciso descobrir quais notas tem no primeiro arquivo que não tem no segundo, fiz a aplicação para isso, porém é muito lento e levaria muito mais muito tempo da forma que fiz, qual melhor forma nesses cenários?

meu código


public class Tarefa implements Runnable {

    private final SplashUI splashUI = new SplashUI();
    private final List<String> faltantes = new ArrayList<String>();
    private int index;

    @Override
    public void run() {

        LocalDateTime inicio = LocalDateTime.now();

        Controle controle = new Controle(new File("NOTAS_SAIDAS_ARQUIVOS.txt"));

        Scanner scanner = null;
        try {
            scanner = new Scanner(new File("NOTAS_LIVROS.txt"));
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        }

        this.splashUI.setVisible(true);
        this.splashUI.setList(faltantes);

        while (scanner.hasNextLine()) {

            this.splashUI.setList(faltantes);

            String linha = scanner.nextLine();

            if (!controle.existe(linha)) {
                faltantes.add(linha);
            }

            this.splashUI.jLabel.setText(index + " linhas processadas");
            index++;
        }

        scanner.close();

        LocalDateTime fim = LocalDateTime.now();
        long hora = ChronoUnit.HOURS.between(inicio, fim);
        long minuto = ChronoUnit.MINUTES.between(inicio, fim);
        long segundo = ChronoUnit.SECONDS.between(inicio, fim);
        long milis = ChronoUnit.MILLIS.between(inicio, fim);

        this.splashUI.jLabel
                .setText(index + "linhas processadas, em " + hora + " : " + minuto + " : " + segundo + " : " + milis);

    }

}

public class Controle {

    private File arquivo;

    public Controle(File file) {
        this.arquivo = file;
    }


    public boolean existe(String texto) {

        try {

            // Assim ficou um pouco mais rápido que usar Scanner
            FileInputStream fis = new FileInputStream(this.arquivo);
            InputStreamReader isr = new InputStreamReader(fis);
            BufferedReader br = new BufferedReader(isr);

            String linha = br.readLine();

            while (linha != null) {
                if (linha.equals(texto)) {
                    br.close();
                    return true;
                }

                linha = br.readLine();
            }

            br.close();
            return false;
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }
}
2 respostas

Consegue enviar uma exemplo de como os dados estão nos arquivos?

Talvez a api NIO seja mais performática, algo como:

List<String> lines = Files.readAllLines(path);
lines.stream().foreach(.......);

que eu saiba o arquivo todo será salvo na memória, sendo mais rápido, mas dependendo do tamanho do arquivo pode acabar a memória do pc.