加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 编程开发 > Java > 正文

java – 如何在Swing中读取和显示大文本文件?

发布时间:2020-12-15 04:21:31 所属栏目:Java 来源:网络整理
导读:这可能听起来有点复杂,我会尽量简化我的要求. 我正在开发的程序可以使用JTextArea从/向文件读写.当文件相当大时,将该文件中的数据读入文本区域需要花费大量时间.作为一个例子,我有一个文件,目前有40,000行文本,大约50个字符一行;还有,一些线包裹.有很多文本,
这可能听起来有点复杂,我会尽量简化我的要求.
我正在开发的程序可以使用JTextArea从/向文件读写.当文件相当大时,将该文件中的数据读入文本区域需要花费大量时间.作为一个例子,我有一个文件,目前有40,000行文本,大约50个字符一行;还有,一些线包裹.有很多文本,从那个文件中读取需要花费更多的时间.

目前,我正在使用标准读取方法,该方法利用JTextArea组件包含的BufferedReader实例.我想要做的是加载JTextArea,并在屏幕上加载一定量的文本.屏幕上的其余部分在后台单独的线程中加载.

使用InputStream并将每个字符写入数组然后将字符写入JTextArea就足够了吗?或者应该采用不同的方法吗?我正在努力实现快速有效的读取方法.

解决方法

手头有两个即时的问题

首先,需要以这样的方式读取文件,以便它可以逐步更新UI而不会导致不可接受的延迟

第二,JTextArea实际处理这一数据量的能力……

第一个问题相对来说很容易修复.您需要确保的是,在读取文件时您没有阻止事件调度线程,并且您只是在事件调度线程的上下文中更新JTextArea.为此,SwingWorker是一个很好的选择,例如……

public class FileReaderWorker extends SwingWorker<List<String>,String> {

    private File file;
    private JTextArea ta;

    public FileReaderWorker(File file,JTextArea ta) {
        this.file = file;
        this.ta = ta;
    }

    public File getFile() {
        return file;
    }

    public JTextArea getTextArea() {
        return ta;
    }

    @Override
    protected List<String> doInBackground() throws Exception {
        List<String> contents = new ArrayList<>(256);
        try (BufferedReader br = new BufferedReader(new FileReader(getFile()))) {
            String text = null;
            while ((text = br.readLine()) != null) {
                // You will want to deal with adding back in the new line characters
                // here if that is important to you...
                contents.add(text);
                publish(text);
            }
        }
        return contents;
    }

    @Override
    protected void done() {
        try {
            get();
        } catch (InterruptedException | ExecutionException ex) {
            ex.printStackTrace();
            // Handle exception here...
        }
    }

    @Override
    protected void process(List<String> chunks) {
        JTextArea ta = getTextArea();
        for (String text : chunks) {
            ta.append(text);
        }
    }

}

有关详细信息,请查看Concurrency in Swing和Worker Threads and SwingWorker

ps-你不需要使用List来存储内容,我只是把它作为一个例子……

第二个问题要复杂得多,需要一些额外的测试以确保它实际上是一个问题,但一般来说,超过1mb的内容往往会导致问题……

为此,您需要能够管理JScrollPane,能够从文件中向后和向前请求文本块,并尝试有效地“捏造”该过程(这样您只需要所需的文本加载,但仍然可以使它看起来像你在JTextArea中加载了所有文本)…

您还可以查看FileChannel,它提供了比标准java.io类更多的功能,包括内存映射,对于初学者,请查看Reading,Writing,and Creating Files.

您还可以考虑使用高度优化的JList或JTable来显示大量数据.这有一些局限性,因为期望固定的行高,当改变时(动态行高)会影响性能,但可能是一个合适的替代方案……

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读