【问题标题】:Web Crawling Using Java Swing使用 Java Swing 进行网络爬取
【发布时间】:2017-06-14 18:05:58
【问题描述】:

我正在开发一个基于 Java 的网络爬虫。我创建了一个 JFrame (Java: Swing)。我的爬虫运行成功。它正在访问已建立的链接。但我想在 JTextArea 中添加动态抓取的链接,但它没有。我不能这样做。当我尝试这个时,我的程序被冻结了。但我可以将访问的 url 设置为控制台。

我的 gui 是这样的:

image

我的代码行是这样的:

    Document html    = null;

    try {
        html = Jsoup.connect(url).get();
        Elements links = html.select("a");

        for(Element link: links) {
            String tmp = link.attr("abs:href");
            jTextArea2.append(tmp + "\n");

            if(!this.visitedUrl.contains(tmp)) {
                this.foundedUrl.add(tmp);
                System.out.println(tmp);
            }
        }

        while(this.foundedUrl.size() > 0) {
            String tmp = this.foundedUrl.get(this.foundedUrl.size() - 1);
            this.foundedUrl.remove(this.foundedUrl.size() - 1);
            if(!this.visitedUrl.contains(tmp)) {
               this.linkTracker(tmp); 
            }
        }

如何在 JTextarea 中动态设置访问的 url?

【问题讨论】:

  • 您是从 UI 事件线程调用此代码吗?大多数 Swing 控件仅支持从 UI 事件线程调用。
  • 欢迎来到 Stack Overflow,请使用tour 并通过help center,这将引导您到How to Ask,稍后会告诉您发布一个有效的minimal reproducible example,以证明您的问题。照原样,您的程序不完整,因此不可编译,我们不想要您的整个应用程序,而是一个简单但完整的示例(不是代码 sn-ps)来证明您的问题。例如,您可以对 URL 进行硬编码,并使用一个 JTextArea 和一个 JButton 来启动该过程。我们知道您的 GUI 冻结,但您的问题过于广泛,因为它缺乏足够的信息(即 MCVE)来回答......
  • ... 因为您可能还没有在 EDT 中初始化您的应用程序,或者您正在 EDT 中运行它,所以您可能也想看看 Swing Worker,这可以让您在单独的线程中处理长任务并且不阻塞 EDT(这会冻结您的 GUI)。另请阅读Concurrency in Swing

标签: java swing web-crawler


【解决方案1】:

试试这个:

new Thread((Runnable)() ->
{
  Document html    = null;

  try {
    html = Jsoup.connect(url).get();
    Elements links = html.select("a");

    for(Element link: links) {
        String tmp = link.attr("abs:href");
        EventQueue.invokeLater(() -> {
           jTextArea2.append(tmp + "\n");
        });

        if(!this.visitedUrl.contains(tmp)) {
            this.foundedUrl.add(tmp);
            System.out.println(tmp);
        }
    }

    while(this.foundedUrl.size() > 0) {
        String tmp = this.foundedUrl.get(this.foundedUrl.size() - 1);
        this.foundedUrl.remove(this.foundedUrl.size() - 1);
        if(!this.visitedUrl.contains(tmp)) {
           this.linkTracker(tmp); 
        }
    }
  }catch(Exception e){}
}).start();

您的 GUI 冻结的原因是您阻塞了 GUI 线程。因此,通过创建一个新线程并从那里运行,在不同的线程上开始您的操作。 然后获取更新调用 EventQue 它会告诉 GUI 线程将文本添加到 JTextArea

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-10-17
    相关资源
    最近更新 更多