A股上市公司传智教育(股票代码 003032)旗下技术交流社区北京昌平校区

 找回密码
 加入黑马

QQ登录

只需一步,快速开始

© 葛旭东 中级黑马   /  2012-10-8 13:40  /  3683 人查看  /  8 人回复  /   0 人收藏 转载请遵从CC协议 禁止商业使用本文

本帖最后由 葛旭东 于 2012-10-8 22:03 编辑

  1.          <div class="blockcode"><blockquote>class Test implements Runnable{
  2. private boolean flag;
  3. Test(boolean flag){
  4. this.flag = flag;
  5. }
  6. Object obj1 = new Object();
  7. Object obj2 = new Object();
  8. public void run(){
  9. if(flag){
  10. synchronized(obj1){
  11. System.out.println(Thread.currentThread().getName()+"  if---obj1");
  12. synchronized(obj2){
  13. System.out.println(Thread.currentThread().getName()+"  if---obj2");
  14. }
  15. }
  16. }
  17. else{
  18. synchronized(obj2){
  19. System.out.println(Thread.currentThread().getName()+"  else---obj2");
  20. synchronized(obj1){
  21. System.out.println(Thread.currentThread().getName()+" else---obj1");
  22. }
  23. }
  24. }
  25. }
  26. }
  27. public class DeadLockTest {

  28. public static void main(String[] args) {

  29.        Thread t1 = new Thread(new Test(true),"1号");
  30.        Thread t2 = new Thread(new Test(false),"2号");
  31.        t1.start();
  32.        t2.start();
  33. }

  34. }
复制代码
这个程序使用两个不同的锁,运行后好像不能造成死锁现象。即使添加循环后多次打印也不会出现死锁,为什么?
老毕的视频中的执行过程中很容易就死锁了。。。

评分

参与人数 1技术分 +1 收起 理由
刘芮铭 + 1 欢迎来15期~~~~

查看全部评分

8 个回复

倒序浏览
  • Thread t1 = new Thread(new Test(true),"1号");
  •        Thread t2 = new Thread(new Test(false),"2号");
  •        t1.start();
  •        t2.start();

你这里建了俩 对象。。。。里面的flag,锁啥的都不共享。。。。。

传一个对象进去就欧了

给你改了改代码   加个循环

  1. class Test implements Runnable{
  2. private boolean flag=true;

  3. Object obj1 = new Object();
  4. Object obj2 = new Object();

  5. public void run()
  6. {
  7. while(true)
  8. {
  9. if(flag)
  10. {
  11.          synchronized(obj1)
  12.         {
  13.                 System.out.println(Thread.currentThread().getName()+"  if---obj1");
  14.                  synchronized(obj2)
  15.                 {
  16.                          System.out.println(Thread.currentThread().getName()+"  if---obj2");
  17.                 }
  18.          }
  19.          flag=false;
  20. }
  21. else
  22. {
  23.          synchronized(obj2)
  24.         {
  25.                  System.out.println(Thread.currentThread().getName()+"  else---obj2");
  26.                  synchronized(obj1)
  27.                 {
  28.                         System.out.println(Thread.currentThread().getName()+" else---obj1");
  29.                  }
  30.         }
  31.         flag=true;
  32. }
  33. }
  34. }
  35. }
  36. class DeadLockTest {

  37. public static void main(String[] args) {

  38.        Test test=new Test();
  39.            Thread t1 = new Thread(test,"1号");
  40.        Thread t2 = new Thread(test,"2号");
  41.        t1.start();
  42.        t2.start();
  43. }

  44. }
复制代码

评分

参与人数 1技术分 +1 收起 理由
刘芮铭 + 1 欢迎来15期~~~~

查看全部评分

回复 使用道具 举报
可是老毕视频中确实传入了两个对象new Test(true)和new Test(false),为什么可以呢?
回复 使用道具 举报
首先你要知道,使用多线程是因为有代码需要被重复执行很多次,所以多创建个线程,让CPU进行切换着执行,提高感观性,用锁是为了解决线程安全问题的。你这个题中如果加上for()循环,第一个线程进来拿到obj1这个锁,第二个线程进来拿到obj2这个锁,第一个线程要执行下面的代码需要拿到obj2这个锁,第二个线程需要拿到obj1这个锁,但是两个线程都在循环中,没有出去,谁也拿不到对方的锁,就造成死锁了。第一个线程调用了start()后需要改标记。

评分

参与人数 1技术分 +1 收起 理由
刘芮铭 + 1 欢迎来15期~~~~

查看全部评分

回复 使用道具 举报
葛旭东 发表于 2012-10-8 14:57
可是老毕视频中确实传入了两个对象new Test(true)和new Test(false),为什么可以呢? ...

能贴下毕老师的 代码吗
回复 使用道具 举报
  1. class Test implements Runnable{
  2.         private boolean flag;
  3.         Test(boolean flag){
  4.                 this.flag = flag;
  5.         }
  6.         public void run(){
  7.                 if(flag){
  8.                         synchronized(MyLock.obj1){
  9.                                 System.out.println(Thread.currentThread().getName()+"  if---obj1");
  10.                                 synchronized(MyLock.obj2){
  11.                                         System.out.println(Thread.currentThread().getName()+"  if---obj2");       
  12.                                
  13.                                 }
  14.                         }
  15.                         flag  = false;
  16.                 }
  17.                 else{
  18.                         synchronized(MyLock.obj2){
  19.                                 System.out.println(Thread.currentThread().getName()+"  else---obj2");
  20.                                 synchronized(MyLock.obj1){
  21.                                         System.out.println(Thread.currentThread().getName()+"  else---obj1");
  22.                                
  23.                                 }
  24.                         }
  25.                         flag = true;
  26.                 }
  27.         }
  28.         }
  29. class MyLock{
  30.         static Object obj1 = new Object();
  31.         static Object obj2 = new Object();
  32. }
  33. public class DeadLockTest {

  34.         public static void main(String[] args) {
  35.                Thread t1 = new Thread(new Test(true));
  36.                Thread t2 = new Thread(new Test(false));
  37.                t1.start();
  38.                t2.start();

  39.         }

  40. }
复制代码
老毕原代码

评分

参与人数 1技术分 +1 收起 理由
刘芮铭 + 1 欢迎来15期~~~~

查看全部评分

回复 使用道具 举报
是两个锁的问题,本类中定义的两个锁,如果一个new Test(),可以死锁,而两个new Test()达不到死锁效果;
而新建类中的两个锁,在两个new Test()可以达到死锁效果。
回复 使用道具 举报
郭阳 中级黑马 2012-10-8 16:52:29
8#
本帖最后由 郭阳 于 2012-10-8 16:54 编辑
葛旭东 发表于 2012-10-8 16:39
是两个锁的问题,本类中定义的两个锁,如果一个new Test(),可以死锁,而两个new Test()达不到死锁效果 ...

你注意看代码了吗 虽然是两个对象,毕老师两个对象用的是同一个锁

在一个类中定义了一个静态的锁

其实理论上和传一个对象是相同的
你之前之所以不能死锁,是因为两个线程各跑各的,锁虽然是同一个名字,但是封装在两个对象中,不是同一个锁,所以互相都影响不到对方。
回复 使用道具 举报
{:soso_e179:}你看的的确仔细啊,确实是一个静态锁。多谢指教!!!{:soso_e183:}
回复 使用道具 举报
您需要登录后才可以回帖 登录 | 加入黑马