如何让我的程序每小时检查一次股票市值[java] [英] how do I make my program check the stock market value every hour[java]

查看:126
本文介绍了如何让我的程序每小时检查一次股票市值[java]的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在制作一个程序来检查股票市场的符号,我做到了这一点,并添加了一个基本的gui。我很困惑如何每小时检查一次,如果增加则创建绿色向上箭头,如果减少则创建红色向下箭头。

I am making a program to check the stock market for a symbol and I got that far, and added a basic gui to it. I am stumped on how to make it check every hour and create a green up arrow if it increased and red down arrow if it decreased.

import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.io.IOException;

import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JTextField;

import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.jsoup.select.Elements;

public class QuoteTracker {
    JFrame frame;
    JPanel mainPanel;
    JLabel enterLabel;
    JLabel resultLabel;
    JTextField text;
    JTextField result;
    JButton query;
    JButton redArrow;
    JButton greenArrow;
    String url; 

    public static void main(String[] args) {
        new QuoteTracker().buildGui();

    }

    public class checkingQuote implements Runnable {

        @Override
        public void run() {
            while (true) {
                try {
                    checkQuote(url);                
                //if increase in value green button

                    System.out.println("Sleeping");
                    Thread.sleep(1000 * 60 * 60);
                    System.out.println("Waking");
                } catch (InterruptedException ie) {
                    ie.printStackTrace();
                    break;
                }
            }
        }

    }

    public void checkQuote(String symbol) {
        try {
            String url = "http://finance.yahoo.com/q?s=" + symbol + "&ql=0";
            this.url = url;
            Document doc = Jsoup.connect(url).get();
            Elements css = doc.select("p > span:first-child > span");
            result.setText(css.text());         
        } catch (IOException e) {

        }

    }

    public void buildGui() {
        frame = new JFrame("QuoteTracker");
        mainPanel = new JPanel();
        enterLabel = new JLabel("enter symbol ");
        resultLabel = new JLabel("result ");
        text = new JTextField(4);
        result = new JTextField(8);
        query = new JButton("query");
        query.addActionListener(new queryListener());

        mainPanel.add(enterLabel);
        mainPanel.add(text);
        mainPanel.add(query);
        mainPanel.add(resultLabel);
        mainPanel.add(result);

        frame.getContentPane().add(mainPanel);
        frame.setSize(300, 400);
        frame.setVisible(true);
        frame.pack();
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    }

    class queryListener implements ActionListener {
        @Override
        public void actionPerformed(ActionEvent ev) {
            checkQuote(text.getText());
        }
    }

}

我是甚至需要一个线程?我以前从来没有做过,并试图添加有意义的东西。我想我要么需要一个线程,要么使用java的Timer?

Do I even need a thread? I've never made one before and tried to add things that made sense. I am thinking I either need a thread or to use java's Timer?

推荐答案

使用 SwingWorker 在更新时在后台执行长时间运行的任务UI基于长期运行任务的一些结果。这意味着,它实际上是两个不同的线程相互通信 - 工作线程事件调度线程(EDT)

Use SwingWorker to execute long running task in the background while updating the UI based on some results from that long running task. That means, it is actually about two different threads communicating to each other - Worker Threads and Event Dispatch Thread (EDT)

但在此之前,我想指出一些关于你的代码的注释。

But before that, I want to point some few notes about your code.


  • 在EDT中调用UI的初始化。也就是说,不是直接调用 new QuoteTracker()。buildGui(),而是在 Runnable 传递给 SwingUtilities.invokeLater (如这个

  • Invoke the initialization of your UI in the EDT. That is, instead of just straightly calling new QuoteTracker().buildGui(), call it inside the run method of a Runnable passed to SwingUtilities.invokeLater (like this)

根据Java标准,类应以大写字母开头。

Classes should start in capital letter as per the Java standard.

在现有代码中应用 SwingWorker ,您可以执行以下操作:

To apply SwingWorker in you existing code, you can do the following :

首先,您必须将 checkQuote 方法放在其他类中(理想情况下是服务) class)然后修改你的 checkQuote 方法以返回设置为textfield 结果的 String 。这样的东西

First, you must place your checkQuote method in some other class (ideally a service class) then modify your checkQuote method to return the String that is set to the textfield result. Something like this

public Class QuoteService{
    public String checkQuote(String symbol) {
        try {
            String url = "http://finance.yahoo.com/q?s=" + symbol + "&ql=0";
            this.url = url;
            Document doc = Jsoup.connect(url).get();
            Elements css = doc.select("p > span:first-child > span");
            return css.text();
        } catch (IOException e) {
            e.printStackTrace();
        }
        return "";
    }
}

然后你可以赚 QuoteTracker 类主要关注应用程序的UI部分。只需将服务对象创建为实例级别字段,以便您可以在类中自由调用 checkQuote 方法。

You can then make your QuoteTracker class to focus mainly in the UI part of your application. Just create the service object as instance level field so that you can freely call checkQuote method within your the class.

单击按钮时调用SwingWorker。

Invoke SwingWorker when the button is clicked.

public void actionPerformed(ActionEvent ev) {

    new SwingWorker<Void, String>() {
        @Override // this method is done in the Worker Thread
        protected Void doInBackground() throws Exception {
            while(true){ 
                String res = checkQuote(text.getText());
                publish(res); //will call the process method
                Thread.sleep(1000 * 60 * 60); //1 hour
            }
        }

        @Override // this method is done in the EDT
        protected void process(List<String> resultList){
            String res = resultList.get(0);

            if(!"".equals(res)){
                result.setText(res);
            }
        }

        @Override // this method is done in the EDT. Executed after executing the doInBackground() method
        protected void done() {
            //... clean up
        }
    }.execute();
}

请注意 done()将在执行 doInBackground()完成后执行,这意味着,在我发布的代码中,由于while循环用于定期调用,因此永远不会执行 checkQuote 是无限的。只需修改它就可以根据需要中断该循环

Note that done() will be executed after the execution of doInBackground() is finished, which means, in the code I posted, it will never be executed since the while loop used to periodically call checkQuote is infinite. Just modify it so that you can interrupt that loop according to your need

进一步阅读: Swing中的并发性

这篇关于如何让我的程序每小时检查一次股票市值[java]的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆