package java_thread.mysynchronized;
//synchronized 锁是所对象还是锁代码
//原文:https://www.cnblogs.com/QQParadise/articles/5059824.html
public class synchronized_test1 {
//在Java中,synchronized关键字是用来控制线程同步的,就是在多线程的环境下,控制synchronized代码段不被多个线程同时执行。synchronized既可以加在一段代码上,也可以加在方法上。
//关键是,不要认为给方法或者代码段加上synchronized就万事大吉
public static void main(String[] args) {
/*for (int i = 0; i < 3; i++) {
Thread thread = new MyThread();
thread.start();
} */
//执行结果:
/*test开始..
test开始..
test开始..
test结束..
test结束..
test结束..
启动了三个线程,每隔线程虽然都有sycn关键字 但是锁得住不是地段代码而是当前线程test 个个线程没有相同对象的引用所以不会产生预期的效果
*/
/* Sync sync=new Sync();
for(int i = 0; i < 3; i++) {
//synchronized(Sync.class) { 这种写法是错误的 因为这个锁需要在线程内才能生效 同理若是这个锁生效,那实现的情况就是多个线程调用main这个方法(自己理解,若是错位,希望各位能够指正。谢谢!)
Thread thread = new Mythread2(sync);
thread.start();
}*/
/* 执行结果:
test开始..
test结束..
test开始..
test结束..
test开始..
test结束..
其传入的是相同的对象 而对象内有相应的对象锁 所以不能并发操作
*/
//synchronized锁住的是代码还是对象。答案是:synchronized锁住的是括号里的对象,而不是代码。对于非static的synchronized方法,锁的就是对象本身也就是this。
/* 那么,如果真的想锁住这段代码,要怎么做?也就是,如果还是最开始的那段代码,每个线程new一个Sync对象,怎么才能让test方法不会被多线程执行。
解决也很简单,只要锁住同一个对象不就行了。例如,synchronized后的括号中锁同一个固定对象,这样就行了。这样是没问题,但是,比较多的做法是让synchronized锁这个类对应的Class对象。
*
*/
for (int i = 0; i < 3; i++) {
Thread thread = new Mythread3();
thread.start();
}
}
}
class MyThread extends Thread {
public void run() {
Sync sync = new Sync();
sync.test();
}
}
class Sync{
public void test() {
System.out.println("test开始..");
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("test结束..");
}
}
class Mythread2 extends Thread{
private Sync sycn2;
public Mythread2(Sync sycn2) {
this.sycn2=sycn2;
}
public void run() {
synchronized(Sync.class) {
sycn2.test();
}
}
}
class Mythread3 extends Thread{
public void run() {
Sync sycn2=new Sync();
synchronized(Sync.class) {
sycn2.test();
}
}
}
//原文:https://www.cnblogs.com/QQParadise/articles/5059824.html
建议各位还是去看看原文章