【问题标题】:Run a function synchronously in another thread在另一个线程中同步运行一个函数
【发布时间】:2014-03-10 12:58:55
【问题描述】:

如何在另一个线程中同步运行一个函数,这意味着主 UI 线程有一个函数调用另一个函数,该函数在另一个线程上工作,等待新线程完成并返回值:

int mainFunction() //this function is on the main UI thread
{
   return doWorkOnNewThread();
}

int doWorkOnNewThread()
{
   //do work on new thread
}

【问题讨论】:

  • 阻塞主 UI 线程有什么意义?如果操作时间过长,您将收到 ANR。
  • 我需要第二个线程的值才能继续主线程的工作。

标签: java android


【解决方案1】:

您可以为此使用异步任务,即使它是异步的。您可以根据需要使用回调 onPostExecute 和 onProgressUpdate 更新值。我还应该注意,您可能不想同步执行此操作,因为它会阻塞您的 UI 线程,这可能会导致应用程序没有响应警报,具体取决于计算需要多长时间。

【讨论】:

  • 我已经在我的 android 应用程序中使用了 AsyncTask,但是如何在 mainFunction() 中等待另一个线程上的工作完成?放置一个始终检查工作是否完成的while循环?这对我来说似乎很丑陋。 mainFunction() 必须从第二个线程返回计算结果。
  • 你永远不应该在你的主线程中等待。这将导致应用程序无响应。您应该做的是在异步任务的 onResult 方法中使用结果更新您需要的视图。因此,如果您要更新文本视图。将该 textView 保存为变量,然后在 textView 上的 onResult 调用 setText 以及计算结果。
  • 但是我还有其他几个必须在另一个线程中运行的函数。然后我将不得不链接它们:一个 onResult 调用另一个异步任务,而这个新异步任务的 onResult 调用另一个异步任务等等等等。这非常非常难看。我只想要一个返回在另一个线程上计算的 int 的函数。
【解决方案2】:

在单独的线程中执行代码的方法很少。 你可以阅读这个here

我认为AsyncTask 会做你想做的事。

protected void onPreExecute () {
    // you can show some ProgressDialog indicating to the user that thread is working
}

protected Type doInBackground(String... args) {
    doWorkOnNewThread()
    // do your stuff here
}

protected void onPostExecute(Type result) {
    // here you can notify your activity that thread finished his job and dismiss ProgressDialog
}

【讨论】:

  • 我已经在我的 android 应用程序中使用了 AsyncTask,但是如何在 mainFunction() 中等待其他线程上的工作完成?放置一个始终检查工作是否完成的while循环?这对我来说似乎很丑陋。 mainFunction() 必须从第二个线程返回计算结果。
  • 你不应该在你的 UI 线程中等待。我认为您的 mainFunction() 应该运行 AsyncTask,然后 AsyncTask 应该在其 onPostExecute() 方法中返回结果。
  • 但是我必须将 5-6 个 onPostExecute() -s 链接在一起,因为下一步使用上一步中的值。这是非常非常丑陋的。
【解决方案3】:

你有两种方法: 1.异步任务 2.处理程序

【讨论】:

    【解决方案4】:
      public static <T> T runSynchronouslyOnBackgroundThread(final Callable<T> callable) {
        T result = new Thread() {
          T callResult;
    
          @Override
          public void run() {
            try {
              callResult = callable.call();
            } catch (Exception e) {
              throw new RuntimeException(e);
            }
          }
    
          T startJoinForResult() {
            start();
            try {
              join();
            } catch (InterruptedException e) {
              throw new RuntimeException(e);
            }
            return callResult;
          }
        }.startJoinForResult();
    
        return result;
      }
    

    【讨论】:

      猜你喜欢
      • 2011-06-25
      • 1970-01-01
      • 2021-12-16
      • 1970-01-01
      • 2016-03-06
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多