0

当我设置数字 [0] = 10 时,我的循环没有停止,while 循环的线程看不到按下 jbutton 时正在更改的数字,我该如何解决这个问题?我相信线程被阻塞了。

    public class A{

        private int[] number = new number[1];
        private number_game gui;


        public A(){
        }

        public void thread_loop(){

            gui = new number_game();
            gui.the_game(number);

            Thread nums = new Thread(){

                public void run(){

                    while(number[0]!= 10){

                           if(number != 10)
                              System.out.println("wrong number")
                    }

                };nums.start();

            } 
        }

    }

public class number_game extends Jframe{

......

    public number_game(){}

    / creating gui
    public void the_game(int [] guess){

       .............
       checkguess.addActionListener(new ActionListener() {
           @Override
           public void actionPerformed(ActionEvent e){

                  guess[1] = 10;
                  dispose();

            }
        });
   }
}

public class main{
    public static void main(String[]args) {

    A nums_play = new A();
    nums_play.thread_loop();
    }

}
4

1 回答 1

1

我希望这只是一些线程练习。要跨线程共享值,您需要确保访问正确同步,虽然有多种方法可以做到这一点,但最简单的一种可能是使用 aAtomicInteger为您处理所有多线程访问功能.

我还包含了一个简单的“锁定”类,这意味着它Thread不会“放任自流”失控,并为 UI 提供一种方法来提醒线程发生了变化,然后它可以处理该值.

所有这些都在线程监视器和 UI 类之间共享。

我强烈建议您查看更详细地涵盖此信息的并发跟踪

import java.awt.HeadlessException;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.ReentrantLock;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;

public class Test extends JFrame {

    public static void main(String[] args) {
        new Test();
    }

    public class CommonLock {

        private ReentrantLock lock;
        private Condition condition;

        public CommonLock() {
            lock = new ReentrantLock();
            condition = lock.newCondition();
        }

        protected void lock() {
            lock.lock();
        }

        protected void unlock() {
            lock.unlock();
        }

        public void await() throws InterruptedException {
            lock();
            try {
                condition.await();
            } finally {
                unlock();
            }
        }

        public void signal() {
            lock();
            try {
                condition.signal();
            } finally {
                unlock();
            }
        }

    }

    public Test() throws HeadlessException {
        CommonLock lock = new CommonLock();
        AtomicInteger value = new AtomicInteger(0);
        ThreadMonitor monitor = new ThreadMonitor(value, lock);
        monitor.start();

        SwingUtilities.invokeLater(new Runnable() {
            @Override
            public void run() {
                JFrame frame = new JFrame();
                frame.add(new TestPane(value, lock));
                frame.pack();
                frame.setLocationRelativeTo(null);
                frame.setVisible(true);
            }
        });
    }

    public class TestPane extends JPanel {

        private final AtomicInteger value;
        private final CommonLock lock;

        public TestPane(AtomicInteger value, CommonLock lock) {
            this.value = value;
            this.lock = lock;
            JButton btn = new JButton("Pick");
            btn.addActionListener(new ActionListener() {
                @Override
                public void actionPerformed(ActionEvent e) {
                    value.addAndGet(2);
                    lock.signal();
                }
            });
            add(btn);
        }

    }

    public class ThreadMonitor {

        private final AtomicInteger value;
        private final CommonLock lock;

        public ThreadMonitor(AtomicInteger value, CommonLock lock) {
            this.value = value;
            this.lock = lock;
        }

        public void start() {
            Thread thread = new Thread(new Runnable() {
                @Override
                public void run() {
                    while (true) {
                        try {
                            lock.await();
                        } catch (InterruptedException ex) {
                        }
                        int number = value.get();
                        if (number == 10) {
                            break;
                        } else {
                            System.out.println("Bad Guess");
                        }
                    }
                    System.out.println("Good guess");
                }
            });
            thread.start();
        }
    }
}

该示例将以 的步长递增值(从02,让您看到处理它的线程,直到它到达10

如果你愿意,你可以创建一个包含 and 的单一类CommonLockAtomicInteger使管理稍微容易一些,但我会留给你

于 2017-06-02T05:37:42.710 回答