6

私はこれを理解するのに少し苦労しています。これが何が起こっているかです。OracleデータベースへのJDBC接続を保持する新しいスレッドを生成しています。データベースに接続するように要求すると、start()メソッドが呼び出されている間、親スレッドは実行を続けますが、子に(別のメソッドで)クエリを実行するように要求すると、親スレッドは子スレッドの待機中にスタックします。その仕事を終える方法。これを修正する方法として何か推測はありますか?前もって感謝します!

public class Main extends Thread{

    public Main()
    {
    }

    public void myCounter() {
        int i = 0;
        DBConnection myConnection = null;
        for(;;)
        {
            i++;

            System.out.println("time: " + i);
            if( i  == 5)
            {
                myConnection = new DBConnection("localhost", 1521, "hr", "hr", "XE");
                myConnection.start();


            }
            if(i == 10)
                try {

                    myConnection.runQuery("Select * from hr.numbers order by dbms_random.value");
                } catch (SQLException e) {
                    e.printStackTrace();
                }
            try {
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }

    public void run()
    {
        myCounter();
    }

    public static void main(String[] args) {

        Main boot = new Main();
        boot.start();

    }

}

public class DBConnection extends Thread{

    Connection myConnection;
    int port;
    String user;
    String password;
    String serviceName;
    String host;


    public void run()
    {
        setUpConnection(host, port, user, password, serviceName);
    }
    /**
     * Sets up variables to create a connection to Oracle.
     *  
     * @param host      host
     * @param port      port
     * @param user      user
     * @param password  password
     */
    public DBConnection(String host, int port, String user, String password, String serviceName)
    {
        this.host = host;
        this.port = port;
        this.user = user;
        this.password = password;
        this.serviceName = serviceName;
    }


    private void setUpConnection(String host, int port, String user,
            String password, String dataBase) {
        System.out.println("-------- Oracle "
                + "JDBC Connection Testing ------------");

        try {

            Class.forName("oracle.jdbc.OracleDriver");

        } catch (ClassNotFoundException e) {

            System.out.println("Couldn't find Oracle JDBC Driver... :-(");
            e.printStackTrace();
            return;

        }

        System.out.println("Oracle JDBC Driver Registered!");
        myConnection = null;
        try {
            myConnection = DriverManager.getConnection(
                    "jdbc:oracle:thin:@//" 
                            + host 
                            + ":" 
                            + port 
                            + "/" 
                            + dataBase,
                            user, password
                    );

        } catch (SQLException e) {

            System.out.println("Connection Failed!");
            e.printStackTrace();
            return;

        }

        if (myConnection != null) {
            System.out.println("Connected to Oracle! :-)");
        } else {
            System.out.println("Failed to make connection!");
        }
    }


    /**
     * Queries the database and returns a ResultSet
     * @param  query            SQL
     * @throws SQLException 
     */
    public  ResultSet runQuery(String query) throws SQLException 
    {
        System.out.println("                                                    [DBConnection] Started Running @ " + (new SimpleDateFormat("HH:mm:ss:S")).format(new Date()));
        ResultSet rs = null;

        Statement stt = myConnection.createStatement();
        rs = stt.executeQuery(query);
        System.out.println("                                                    [DBConnection] Finished Running @: " + (new SimpleDateFormat("HH:mm:ss:S")).format(new Date()));
        return  rs;

    }

これが私が得る出力です:

time: 1
time: 2
time: 3
time: 4
time: 5
-------- Oracle JDBC Connection Testing ------------
Oracle JDBC Driver Registered!
time: 6
Connected to Oracle! :-)
time: 7
time: 8
time: 9
time: 10
                                                    [DBConnection] Started Running @ 14:46:00:660
                                                    [DBConnection] Finished Running @: 14:46:12:750
time: 11
time: 12
time: 13
time: 14

........。

4

3 に答える 3

6

スレッドがどのように機能するかを少し誤解していると思います。問題は、これを親スレッドで呼び出していることです。

myConnection.runQuery("Select * from hr.numbers order by dbms_random.value");

これは、たまたまスレッドであるオブジェクトに対するrunQueryメソッドの順次呼び出しです。これは、メソッドを実行するように子に指示することを意味するものではありません。代わりに、親はそれ自体を実行し、子スレッドはそのメソッドが返されるとすぐに終了します。myConnectionrun

クエリを実行するためのコマンドを受信し続ける別のスレッドが必要な場合は、親が子が実行するコマンドをキューに入れ続ける、生産者/消費者パターンを実装する必要があります。この目的のために、 ExecutorServiceを確認することをお勧めします。

于 2012-08-21T13:58:30.250 に答える
2

を呼び出すと、親スレッドmyConnection.runQuery()のメソッド内にいるため、そのメソッドの1つを呼び出してもスレッド内にはいません。run()connection

のメソッドrunQuery内を呼び出して、目的を達成する必要があります。run()myConnection

于 2012-08-21T13:59:57.067 に答える
1

メインスレッドrunQueryでメソッドを呼び出したため、メソッドはブロックされています(したがって、クエリが終了するまで待機します)。別のスレッドで呼び出す場合は、他のスレッドrunメソッドで呼び出します(クエリメソッドを最初に呼び出した場所で他のスレッドを開始するだけです)。

于 2012-08-21T14:00:44.917 に答える