假设我有一个带有2个公共静态方法的类,它控制着它自己的单个私有实例。该课程的基本结构如下:
public class MyClass {
private static MyClass myclass = null;
private final Process, OutputStreamWriter, Strings, ints, etc....
private class constructor....
private class methods....
public static void command(String cmd) {
if(myclass == null) {
myclass = new MyClass();
}
myclass.setCmd(cmd);
}
public static void execute() {
myclass.run();
myclass.close();
}
}
我在Android应用程序中使用它,我只是想在我进行远程设计之前验证它是如何工作的。假设该类的命令来自UI线程。 UI线程调用第一个静态方法
MyClass.command("parse and do what's in this string");
现在我希望MyClass.execute()调用在某些情况下可能需要几乎一秒才能完成。我基本上只想验证如果我从Service或Runnable调用MyClass.execute()方法,那么执行将在该线程上发生。
在帖子static-method-behavior-in-multi-threaded-environment-in-java selig中声明:
java中的内存分为两类 - 堆和堆栈。堆是所有对象都存在的地方,堆栈是线程工作的地方。每个线程都有自己的堆栈,无法访问其他堆栈。每个线程还有一个指向代码的指针,指向它们当前正在运行的代码位。
当一个线程开始运行一个新方法时,它将该方法中的参数和局部变量保存在它自己的堆栈上。这些值中的一些可能是指向堆上对象的指针。如果两个线程同时运行相同的方法,它们的代码指针都会指向该方法,并且在它们的堆栈上有自己的参数和局部变量副本....
现在,由于UI线程调用了静态方法MyClass.command(“Do this”),它在技术上实例化了该类的私有本地参数和变量,这意味着该类位于UI线程的堆???这意味着如果我从服务线程或可运行线程调用MyClass.execute(),实际执行将在UI线程上发生,而服务或runnable等待它?我对此的理解是否正确?
谢谢!
答案 0 :(得分:4)
好的,你的帖子中有很多错误信息。
1)默认情况下,服务和Runnables没有自己的线程。服务在UI线程上运行,尽管它们可以创建一个线程(默认情况下IntentService会这样做)。 Runnables在运行它们的任何线程调用上运行。但除非你将它们发布到附加到另一个线程或Thread对象的Handler,否则他们不会开始一个新的。
2)所有Java对象都在堆上,而不是堆栈。堆栈只保存基本类型和对象的引用(但对象本身在堆上)。
3)是的,每个Thread都有自己的堆栈,因此它可以拥有自己的一组局部变量。但这并不能阻止它接触堆上的任何东西。这包括程序中的任何对象
4)Thread中唯一私有的东西是函数中的局部变量。并注意到任何本地对象仍然在堆上,并且可以保存对它的引用并将其传递给另一个线程。
5)绝对没有什么限制线程只调用静态方法。您可以调用任何类型的方法。
答案 1 :(得分:1)
类不在堆栈上。线程和类之间没有交互。
如果调用方法(包括MyClass.execute()
),该方法将在与调用者相同的线程上运行。因此,如果您从服务中调用它,它将在服务的线程中运行(但请注意,这也可能是UI线程,除非您使服务在单独的线程中运行!)。如果你从一个随机线程调用它,它将在该线程上运行。
堆栈对于理解Java代码的作用并不重要。
答案 2 :(得分:1)
这是否意味着该类位于UI线程的堆栈中?
您正在混淆引用和对象。
Java中的对象总是。每个线程都有自己的引用副本到自己堆栈中的对象。因此,command()
所做的任何更改都会影响其引用位于堆栈上的对象 - 引用本身以及堆栈上的所有其他值都将保持不变,因为实体正在被更改在堆上。
这意味着如果我从服务线程或可运行线程调用MyClass.execute(),那么当服务或runnable等待它时,UI线程上是否会发生实际的执行?
如果从另一个线程调用MyClass.execute()
,则execute()
的代码将在该不同的线程上执行。每个线程都会跟踪其他线程正在执行独立的代码。因此,如果您从另一个线程调用MyClass.execute()
,执行将不神奇地传输到UI线程,并且将独立于其他线程发生,但任何共享对象除外。