从主线程共享对象和控制线程执行

时间:2012-02-19 12:29:56

标签: java concurrency mutual-exclusion

我正在努力解决相当容易的问题。我有一个主线程,它绘制一个帧和另一个线程(FrameThread),每次都准备这个帧。两个线程都应该共享相同的MyFrame对象。我想从主线程控制FrameThread,即:MyFrame准备就绪 - >在主线程中绘制它 - >保持FrameThread运行。目前我做了以下事项:

private class FrameEngine
{
    private boolean isFrameReady = false;
    private MyFrame frame;

    public synchronized void generateFrame()
    {
        while(isFrameReady)
            wait();
        frame = FrameGenerator.nextFrame();
        isFrameReady = true;
        notifyAll();
    }

    public synchronized MyFrame getFrame()
    {
        while(!isFrameReady)   
            wait();
        isFrameReady = false;
        notifyAll();
        return frame;
    }
}    

之后我创建了FrameThread:

private class FrameThread implements Runnable
{
    private final FrameEngine frame_eng;

    public FrameThread( FrameEngine engine )
    {
        frame_eng = engine;
    }
    @Override
    public void run()
    {
        while(true)
            frame_eng.generateFrame();
    }
}

最后主线:

FrameEngine frame_engine = new FrameEngine();
Thread frameThread = new Thread( new FrameThread( frame_engine ) );
frameThread.start();
...
while(true)
{
    ...
    drawFrame( frame_engine.getFrame() ); 
    ...
}

所以我的目标是:FrameThread在后台执行,并在帧准备好后立即停止。我是Java的新手,我觉得有更好,更安全的方法来实现它。你能给我一个建议吗?谢谢。

1 个答案:

答案 0 :(得分:1)

这是典型的生产者 - 消费者问题。我建议你避免使用wait()和notify()因为它们很难做对,即使是经验丰富的开发人员也是如此。

相反,请查看BlockingQueue界面,并使用评论中的示例作为指导。这似乎正是您正在寻找的。

如果要求提前生成的帧数不超过一帧,请使用容量为1的ArrayBlockingQueue

我还应该提到,在您的示例和上面链接中的BlockingQueue示例中,没有解释关闭生产者和消费者线程的语义。您需要添加一个完整的停止机制,否则即使主线程已经死亡,您的程序也不会自行关闭。