如何在 Activity 和其他 Activity 创建的线程之间进行通信
How to communicate between Activity and Threads created by other Actvity
当您有 2 个 Activity(A 和 B)并且 A 是 MainActivity 时,现在您启动您的 App,A 启动 B。
B 是一个 activity,带有一个与用户交互的对话框,创建一个蓝牙连接和 2 个线程,1 个接收和一个发送。
现在,将信息从 A 发送到 B 线程的最佳方式是什么?
一开始我用的是静态的WeakReference,但是听说这会导致很多问题,所以想求一个更通用的解决方案。
请记住,当从另一个 Activity 启动一个 Activity 时,您只能传递 Serializable Objs 和简单数据。所以不可能以这种方式使用处理程序。
这是我使用的静态弱引用:
public class T1 extends Thread{
private static WeakReference<T1> weak_T1;
public void T1 (){
weak_T1 = new WeakReference<T1> (This);
}
public static WeakReference getWeakReverence() {
return weak_T1;
}
}
这是在堆栈中查找 运行 线程的方法:
for (Thread thread : Thread.getAllStackTraces().keySet()) {
if (thread.getName().equalsIgnoreCase("T1")){
T1A =thread;
}else if (thread.getName().equalsIgnoreCase("T2")){
T2A =thread;
}
}
另一种可能的解决方案:
public class example extends Thread {
private static example instance;
private example() {
}
public static example getIsntance(){
if(instance == null){
instance = new example();
}
return instance;
}
}
WeakReference
可能不是您想要的。也就是说,假设您的 Thread 对象不会终止,或者在 Activity B 停止后以某种方式维护一些对 Activity A 有用的信息。如果您使用 WeakReference
,它可能会在 Activity B 结束后立即变为 "null",线程终止。只需使用常规的旧强引用。它将确保 T1 和包含的信息继续存在,直到您完成它。
public class ActivityB extends Activity
{
private T1 t1;
@Override
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
t1 = startMyThread();
}
@Override
public void onBackPressed()
{
ActivityA.tempT1 = t1;
//This technique presumes that Activity A is guaranteed to resume after a
//back button press, based on the arrangement of your backstack, etc. If
//Activity A is started via some other means (e.g., an explicit startActivity(),
//finish(), etc.), then this reference will have to be set prior to
//that call, as well, in order to establish the appropriate "happens before" relationship.
//If you fail to ensure that Activity A resumes after this point, you will
//risk a memory leak.
super.onBackPressed();
}
}
public class ActivityA extends Activity
{
public static T1 tempT1 = null;
private T1 t1;
@Override
public void onResume()
{
super.onResume();
if(tempT1 == null)
{
//Apparently, Activity B hasn't executed yet. Provide the user with a button to start it.
}
else
{
t1 = tempT1;
tempT1 = null; //To avoid a memory leak
//We just retrieved the reference that Activity B left for us.
//Now, change UI states so that the user can see information about t1.
}
}
}
当您有 2 个 Activity(A 和 B)并且 A 是 MainActivity 时,现在您启动您的 App,A 启动 B。
B 是一个 activity,带有一个与用户交互的对话框,创建一个蓝牙连接和 2 个线程,1 个接收和一个发送。
现在,将信息从 A 发送到 B 线程的最佳方式是什么?
一开始我用的是静态的WeakReference,但是听说这会导致很多问题,所以想求一个更通用的解决方案。
请记住,当从另一个 Activity 启动一个 Activity 时,您只能传递 Serializable Objs 和简单数据。所以不可能以这种方式使用处理程序。
这是我使用的静态弱引用:
public class T1 extends Thread{
private static WeakReference<T1> weak_T1;
public void T1 (){
weak_T1 = new WeakReference<T1> (This);
}
public static WeakReference getWeakReverence() {
return weak_T1;
}
}
这是在堆栈中查找 运行 线程的方法:
for (Thread thread : Thread.getAllStackTraces().keySet()) {
if (thread.getName().equalsIgnoreCase("T1")){
T1A =thread;
}else if (thread.getName().equalsIgnoreCase("T2")){
T2A =thread;
}
}
另一种可能的解决方案:
public class example extends Thread {
private static example instance;
private example() {
}
public static example getIsntance(){
if(instance == null){
instance = new example();
}
return instance;
}
}
WeakReference
可能不是您想要的。也就是说,假设您的 Thread 对象不会终止,或者在 Activity B 停止后以某种方式维护一些对 Activity A 有用的信息。如果您使用 WeakReference
,它可能会在 Activity B 结束后立即变为 "null",线程终止。只需使用常规的旧强引用。它将确保 T1 和包含的信息继续存在,直到您完成它。
public class ActivityB extends Activity
{
private T1 t1;
@Override
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
t1 = startMyThread();
}
@Override
public void onBackPressed()
{
ActivityA.tempT1 = t1;
//This technique presumes that Activity A is guaranteed to resume after a
//back button press, based on the arrangement of your backstack, etc. If
//Activity A is started via some other means (e.g., an explicit startActivity(),
//finish(), etc.), then this reference will have to be set prior to
//that call, as well, in order to establish the appropriate "happens before" relationship.
//If you fail to ensure that Activity A resumes after this point, you will
//risk a memory leak.
super.onBackPressed();
}
}
public class ActivityA extends Activity
{
public static T1 tempT1 = null;
private T1 t1;
@Override
public void onResume()
{
super.onResume();
if(tempT1 == null)
{
//Apparently, Activity B hasn't executed yet. Provide the user with a button to start it.
}
else
{
t1 = tempT1;
tempT1 = null; //To avoid a memory leak
//We just retrieved the reference that Activity B left for us.
//Now, change UI states so that the user can see information about t1.
}
}
}