public class mainfile { static int num = 5000; public static void main(String[] args) throws InterruptedException {
myThreadClass1 thread1 = new myThreadClass1();
myThreadClass2 thread2 = new myThreadClass2(); Thread t1 = new Thread(thread1);
Thread t2 = new Thread(thread2); t1.setPriority(4);
t2.setPriority(4); t1.start();
t2.start(); }
}class myThreadClass1 implements Runnable { myThreadClass1() { } public synchronized void run() {
System.out.println("Created thread"); while (mainfile.num > 0) {
mainfile.num--;
System.out.println("thread 1:sell 1.leaving:" + mainfile.num + ";");
}
}
}class myThreadClass2 implements Runnable { myThreadClass2() { } public synchronized void run() {
System.out.println("Created thread"); while (mainfile.num > 0) {
mainfile.num--;
System.out.println("thread 2:sell 1.leaving:" + mainfile.num + ";"); }
}}
执行结果中为什么1线程和2线程轮流切换访问资源,而不是1进程执行完后执行2进程。
另外输出剩余数量时,为什么有的剩余数量会滞后输出。
解决方案 »
- 关于自定义JTabbedPane的自定义TabComponet的问题
- 为什么会报错,因为是涉及父类?
- 怎么样把应用程序置于顶层
- 请问各位,做的GUI是用在windows还是用在手机,java做的GUI在PC机上真的有价值吗???
- jbuilder中在一个工程中加入一个web module,在src中的java编译后可以自动copy到web-inf\classes目录下,但是src下的xml文件和properties
- JLabel背景色设置???
- 我也问一个类型转换的问题(高手请进)
- 这样比较判断两个byte型的是否相等?
- jButton1按钮事件里try{}catch(这里怎么写){}
- 利用java如何探测位于局域网内的电脑的ip地址?
- java与数据库的问题
- 如何阻塞键盘输入和鼠标输入
在你的程序执行的过程成会产生一个mainfile 进程。在这个进程中你有创建了两个线程。
线程的执行是并行的而不是你理解串行。在有先级相同的情况下,执行那个取决与操作系统的选择。
你这是创建了两个独立的线程,虽然访问的是统一个资源。但是每个线程是在自己的方法中调用的,对与不同的线程来说,他们访问的都是自己的资源,没有同步的问题。把函数改成这样就会存在同步问题了。
static int num = 5000; public static void main(String[] args) throws InterruptedException {
myThreadClass1 thread1 = new myThreadClass1();
//myThreadClass1 thread2 = new myThreadClass2(); Thread t1 = new Thread(thread1);
Thread t2 = new Thread(thread1); t1.setPriority(4);
t2.setPriority(4); t1.start();
t2.start(); }
synchronized有两种使用方法,一种是synchronized(对象){}代码块,那个小括号里的对象就是“索旗标”,当一个线程执行该代码块时,它将索旗标关闭,其他线程无法执行这段代码。当这个执行完这段代码时,将索旗标打开,这时其他线程就可以执行这段代码了,以此类推;
另外一种就是在方法前面加“synchronized”。那么这个方法 就和上面那个代码块类似。不过这里的“索旗标”对应的对象是“this”对象。
你上述的代码没有同步,是因为 两个run方法的索旗标分别是两个对象--分别是两个类中的this对象。而索旗标只有一个时才能起到作用。
需要达到执行完线程1后再执行线程2,代码应改成如下这般:
ps:以后记得类名首字母大写……public class mainfile { static int num = 100;//5000; 改成100容易看得清楚一些 public static void main(String[] args) throws InterruptedException {
mainfile main = new mainfile(); myThreadClass1 thread1 = new myThreadClass1(main);
myThreadClass2 thread2 = new myThreadClass2(main); Thread t1 = new Thread(thread1);
Thread t2 = new Thread(thread2); t1.setPriority(4);
t2.setPriority(4); t1.start();
t2.start(); } public synchronized void subtract(String id) { while (mainfile.num > 0) {
mainfile.num--;
System.out.println("threadId: " + id + " num: " + mainfile.num + ";");
}
// 线程1完成后num变为0,为了让线程2也能正常执行,恢复它的初始值
mainfile.num = 100;
}
}class myThreadClass1 implements Runnable {
private mainfile main;
myThreadClass1(mainfile main) {
this.main = main;
} public void run() {
System.out.println("Created thread"); this.main.subtract("id1");
}
}class myThreadClass2 implements Runnable { private mainfile main;
myThreadClass2(mainfile main) {
this.main = main;
} public void run() {
System.out.println("Created thread"); this.main.subtract("id2");
}}
1:在这两个函数内部都定义一个synchronized代码块,使它们的索旗标是同一个对象;
2:这两个函数放在同一个类中,那么它们的索旗标都是这个类中的"this"对象;
String str = ""; //为两个类中的synchronized代码块提供同一个索旗标
myThreadClass1 thread1 = new myThreadClass1(str);
myThreadClass2 thread2 = new myThreadClass2(str); Thread t1 = new Thread(thread1);
Thread t2 = new Thread(thread2); t1.start();
t2.start();
}
}class myThreadClass1 implements Runnable { String str = null;
myThreadClass1(String s1) {
this.str = s1;
} public void run() {
synchronized(str){
System.out.println("Created thread");
while (mainfile.num > 50) {
mainfile.num--;
System.out.println("thread 1:sell 1.leaving:" + mainfile.num + ";");
}
}
}
}class myThreadClass2 implements Runnable {
String str = null;
myThreadClass2(String s2) {
this.str = s2;
} public void run() {
synchronized(str){
System.out.println("Created thread"); while (mainfile.num > 0) {
mainfile.num--;
System.out.println("thread 2:sell 1.leaving:" + mainfile.num + ";");
}
}
}
}
看看是不是你的意思
private C c;
public A(C c){
this.c = c;
}
public void run(){
......
synchronized(c){
......
}
......
}
}
class B implements Runnable{
private C c;
public B(C c){
this.c = c;
}
public void run(){
......
synchronized(c){
......
}
......
}
}class Test{
public static void main(String []args){
C c = new C();
A a = new A(c);
B b = new B(c);
Thread t1 = new Thread(A);
Thread t2 = new Thread(B);
...... }
}这样A和B中存在同一对象c,当线程中使用
synchronized(c){
......
}
这样的程序快,或者是调用了使用synchronized修饰的C的方法时,调用者就锁住了对象c,这时其它想要通过这种方法锁对象c的调用者,都会被暂停,直到第一个锁住对象的调用者释放c的锁(synchronized块执行完、c的同步方法执行2完或调用了c.wait()释放锁)为止,这样就达到了同步的目的。