【问题标题】:Synchronized block not executed同步块未执行
【发布时间】:2018-10-24 08:30:38
【问题描述】:

我有 Java Applet,我从 JavaScript 运行文件选择方法。
由于安全不允许这样做,我有一个线程来监视boolean 标志

Thread uploadFilesThread = new Thread(() -> {
    try {
        while (true) {
            synchronized (_UploadFilesSyncObj) {
                _UploadFilesSyncObj.wait();

                if (uploadFiles) {
                    uploadFiles = false;
                    ProcessFiles();
                }
            }
        }
    } catch (Exception ex) {
        // TODO
    }
});
uploadFilesThread.start();

在此方法中,我上传选定的文件。我想要取消逻辑,并在每个上传的文件后检查适当的标志。

volatile boolean _CancelRequested = false;

for (JFileInfo fileEntry : _SelectedFilesList) {
    try {
        synchronized (_CancelSyncObj) {
            if (_CancelRequested) {
                JOptionPane.showMessageDialog(null, "FOR Cancel Requested");
                break;
            }
        }
...

设置标志的方法是:

public void Cancel() {
    synchronized (_CancelSyncObj) {
        _CancelRequested = true;
    }
}

我知道 Cancel 方法肯定是从 javaScript 调用的,如果我把通知窗口放在那里,它将显示出来。但是,“上传者”线程不处理取消,文件上传继续。
我在没有volatilesynchronized 的情况下尝试过,有时可以处理但结果不稳定(据我了解,没有volatilesynchronized 是正确的)。

我是 Java 新手,如果有任何建议,我将不胜感激。

【问题讨论】:

  • 这似乎是一个比使用阻塞队列更难的解决方案。
  • @AndyTurner 我这样做是因为在设置标志后我只需要一个操作,通过收集我可以在队列中添加多个要处理的作业,但无论如何这部分工作,并取消标志没有

标签: java applet synchronized


【解决方案1】:

使用信号量代替 volatile 变量,它将可靠地工作。

关于 volatile 的长篇故事如下: https://www.ibm.com/developerworks/java/library/j-jtp06197/index.html

这里是信号量的示例代码: https://www.geeksforgeeks.org/semaphore-in-java/

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2019-02-27
    • 2013-04-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-02-05
    相关资源
    最近更新 更多