【问题标题】:Call adapter.notifyDataSetChanged() from another thread从另一个线程调用 adapter.notifyDataSetChanged()
【发布时间】:2016-06-01 16:55:07
【问题描述】:

我想从另一个线程调用adapter.notifyDataSetChanged()。我读到我应该使用AsyncTask 并在执行后执行adapter.notifyDataSetChanged()

我必须仅在当前活动(可能是父活动或子活动)上每 5 秒执行一次AsyncTask,因为只有一个活动可以同时执行异步任务。

我是否应该创建一个 TimerTask,它每 5 秒执行一次 AsyncTask,当我开始另一个活动时停止它并在 onResume 中重新启动它?

这是我用于更新当前活动的ListView 的线程的代码。

private void runEventHandler() {
    new Thread() {
        public void run() {
            while (true) {
                try {
                    runOnUiThread(new Runnable() {

                        @Override
                        public void run() {
                            users.add(new User(10, "a", false));
                            adapter.notifyDataSetChanged();
                        }
                    });
                    Thread.sleep(1000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        }
    }.start();
}

现在我必须能够在添加新用户时更新子活动的ListViews

【问题讨论】:

  • 您可以使用runOnUiThread。更多信息请查看stackoverflow.com/questions/11140285/how-to-use-runonuithread
  • 它运行良好,但是当我启动子活动时它会继续运行。我怎样才能停止它然后重新启动它?或者如果可能的话,我可以从线程更新子活动吗?
  • 您可以在线程中使用标志,在线程之外更改标志以暂停或停止它们。如果您将代码放在这里,我可以为您提供更好的帮助。
  • 我添加了代码!
  • 你的意思是你在活动“A”中,例如,“runEventHandler()”函数是“A”函数,在“A”中你调用“runEventHandler()”,你希望你的活动“B”中的列表更新了吗?我没听错吗?

标签: java android multithreading listview android-asynctask


【解决方案1】:

一种可能的方法是您在两个活动中创建一个标志来控制要运行的线程(以下代码不可运行,只是示例以了解您可以做什么):

Activity A
{
public static boolean stopThread = false;
    @Override
    public void onResume()
    {
     super.onResume();
    // put your code here...
     stopThread =false;
     runEventHandler();
     }
private void runEventHandler() {
new Thread() {
    public void run() {
        while (A.stopThread != false) {
            try {
                runOnUiThread(new Runnable() {

                    @Override
                    public void run() {
                        users.add(new User(10, "a", false));
                        adapter.notifyDataSetChanged();
                    }
                });
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }
}.start();
}


  @Override
protected void onStop(){
    super.onStop();
    stopThread =true;
   }

}



Activity B
{
public static boolean stopThread = false;
    @Override
    public void onResume()
    {
     super.onResume();
    // put your code here...
     stopThread =false;
     runEventHandler();
     }
private void runEventHandler() {
new Thread() {
    public void run() {
        while (B.stopThread != false) {
            try {
                runOnUiThread(new Runnable() {

                    @Override
                    public void run() {
                        users.add(new User(10, "a", false));
                        adapter.notifyDataSetChanged();
                    }
                });
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }
}.start();
}


  @Override
protected void onStop(){
    super.onStop();
    stopThread =true;
   }

}

您也可以使用onPause() 代替onStop()。取决于您的程序概念。

【讨论】:

  • 谢谢,我想我会用的。但是,您不认为有比在需要更新的每个活动中创建线程更清洁的方法吗?
  • 还有其他方法可以使您的适配器静态化,然后从后台运行的服务中调用“notifyDataSetChanged”。
【解决方案2】:

您应该像下面的链接中那样使用 timertask:https://examples.javacodegeeks.com/android/core/activity/android-timertask-example/

如果您在不同的线程(如 AsyncTask 的 doInBackground)中,则在 UIThread 上发布任何更改的代码:

runOnUiThread(new Runnable() {

                            @Override
                            public void run() {
                                // Here you can set your Ui Components
                            }
                        });

【讨论】:

    猜你喜欢
    • 2019-07-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-08-13
    • 2015-06-07
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多