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

 找回密码
 加入黑马

QQ登录

只需一步,快速开始

© kira 中级黑马   /  2014-1-21 23:54  /  2064 人查看  /  10 人回复  /   0 人收藏 转载请遵从CC协议 禁止商业使用本文

本帖最后由 kira 于 2014-1-22 14:35 编辑

各位大神 我又来了{:soso_e104:}
今天复习到线程通信机制 发现有一点还是没搞对
比如说 我现在想写一个拉煤的例子 一个送 一个出
我设了两个煤线程 同时开启 循环两千次应该会交叉显示才对 可是发现 根本就执行不到if
不说了 上代码
public class CoalDemo {

        /**
         * @param args
         */
        public static void main(String[] args) {
                Coal coal = new Coal();
                Coal1 c1 = new Coal1(coal);
                Coal2 c2 = new Coal2(coal);
                Thread t1 = new Thread(c1);
                Thread t2 = new Thread(c2);
                t1.start();
                t2.start();

        }

}

class Coal1 implements Runnable{//煤1
        private Coal coal;

        Coal1(Coal coal){
               
                this.coal=coal;
        }

        @Override
        public void run() {
                boolean flag =true;//这里定义了简单的true false循环方法
        
                for(int y=0;y<2000;y++){
                        
                        if(flag){//这里执行不到
                                coal.name="煤炭1";
                                coal.value="1吨";
                                flag = false;
                        }
                        else{
                                coal.name="煤炭2";
                                coal.value="2吨";
                                flag = true;
                        
                        }
                        
        
                        
                }
               
        }
        
        
}

class Coal2 implements Runnable{//煤2
        private Coal coal;
        Coal2(Coal coal){
                this.coal=coal;
        }

        

        @Override
        public void run() {
                for(int z=0;z<2000;z++){//循环运行
                        System.out.println(coal.name+"...."+coal.value);
                }
               
        }
        
        
        
        
}
class Coal{//建立了一堆煤
        
        String name;
        String value;
        
}

打印结果 始终是 煤炭2....2吨
我是想让1和2交叉显示
先不管同步的问题
求哪位大神解答一下 感激不尽{:soso_e136:}

评分

参与人数 1技术分 +1 收起 理由
黄晓鑫 + 1

查看全部评分

10 个回复

倒序浏览
  1. public class CoalDemo2 {

  2.         public static void main(String[] args) {
  3.                 Coal1 c1 = new Coal1();
  4.                 Coal2 c2 = new Coal2();
  5.                 Thread t1 = new Thread(c1);
  6.                 Thread t2 = new Thread(c2);
  7.                 t1.start();
  8.                 t2.start();

  9.         }

  10. }

  11. class Coal1 implements Runnable {//煤1

  12.         public void run() {
  13.         
  14.                 for(int y=0;y<2000;y++){
  15.                         
  16.                           System.out.println("煤....1吨");
  17.                         
  18.                         }
  19.         }
  20.         
  21. }

  22. class Coal2 implements Runnable {//煤2
  23.       
  24.         public void run() {
  25.                 for(int z=0;z<2000;z++){//循环运行
  26.                         System.out.println("煤二....2吨");
  27.                 }
  28.         }
  29.         
  30. }
复制代码
因为Coal1和Coal2是两个类,当建立不同的线程,在栈内存中分配的是不同的空间,所在你通过flag设置的值不能共享,它们是无效的。你的代码也不能动态的设置煤的名称和吨数。如果仅仅是为了测试的话,为什么不在建立自自的对象的时候,把要打印的结果打印呢。

评分

参与人数 1技术分 +1 收起 理由
黄晓鑫 + 1

查看全部评分

回复 使用道具 举报
dapeng111 发表于 2014-1-22 10:16
因为Coal1和Coal2是两个类,当建立不同的线程,在栈内存中分配的是不同的空间,所在你通过flag设置的值不能 ...

没有看懂啊 哥们 如果不能设置布尔值共享的话 这个如何做呢 求解答:)
回复 使用道具 举报
{:soso_e136:}求不沉
回复 使用道具 举报
kira 发表于 2014-1-22 11:15
没有看懂啊 哥们 如果不能设置布尔值共享的话 这个如何做呢 求解答
  1. public class CoalDemo {

  2.         public static void main(String[] args) {
  3.                 Coal c1 = new Coal("煤一","1吨");  //创建对象
  4.                 Coal c2 = new Coal("煤二","2吨");
  5.                 Thread t1 = new Thread(c1);  //创建线程
  6.                 Thread t2 = new Thread(c2);
  7.                 t1.start();   //线程启动
  8.                 t2.start();

  9.         }

  10. }

  11. class Coal  implements Runnable {
  12.                 private String name;
  13.                 private String value;
  14.                
  15.                 Coal(String name, String value) { //构造参数传入值
  16.                         this.name = name;
  17.                         this.value = value;
  18.                 }
  19.         public void run() {
  20.         
  21.                 for(int y=0;y<2000;y++){
  22.                         
  23.                           System.out.println(name + "...."+ value);
  24.                         
  25.                         }
  26.         }
  27.         
  28. }
复制代码
回复 使用道具 举报

但这样做的话 和我当初的初衷不符啊 我最初设想的是两个媒类 这个实际上不是煤 是出口 一个出 一个近这种
可以认为是两个出口 利用这两个出口利用一个资源 在各分成两个线程
这种的话 不就成了只是一个口 利用一堆煤这种了么:)
回复 使用道具 举报
你第一个线程中的代码运行是非常快的,t2.start()时,t1都可能运行完了。
2000次太少了,要想看到交替显示把for循环改成while(true)

看看我的测试结果,你就明白了。。

public class CoalDemo {

    public static void main(String[] args) {
            Coal coal = new Coal();
            Coal1 c1 = new Coal1(coal);
            Coal2 c2 = new Coal2(coal);
            Thread t1 = new Thread(c1);
            Thread t2 = new Thread(c2);
            t1.start();
            t2.start();

    }

}

class Coal1 implements Runnable{//煤1
    private Coal coal;

    Coal1(Coal coal){
            
            this.coal=coal;
    }

    @Override
    public void run() {
         boolean flag =true;
          for(int y=0;y<2000;y++){
                  
                    if(flag){//这里执行不到
                            coal.name="煤炭1";
                            coal.value="1吨";
                           
                            flag = false;  
                    }
                    else{
                           
                            coal.name="煤炭2";
                            coal.value="2吨";   
                           
                            flag = true;
                    
                    }
   
           }
         
         System.out.println("t1运行结束");
         System.out.println("这时候煤炭确定为+"+coal.name+"....."+coal.value);
            
    }
   
}

class Coal2 implements Runnable{//煤2
    private Coal coal;
    Coal2(Coal coal){
            this.coal=coal;
    }

   
    @Override
    public void run() {
           for(int z=0;z<2000;z++){//循环运行
                    System.out.println(coal.name+"...."+coal.value);
           }
      
    }   
   
}
class Coal{//建立了一堆煤
   
    String name;
    String value;
   
}

评分

参与人数 1技术分 +1 收起 理由
黄晓鑫 + 1

查看全部评分

回复 使用道具 举报
kira 中级黑马 2014-1-22 11:54:53
8#
淡夜清风 发表于 2014-1-22 11:52
你第一个线程中的代码运行是非常快的,t2.start()时,t1都可能运行完了。
2000次太少了,要想看到交替显示 ...

额 while(true)这种 在我机子的eclipse里 经常会蹦
实际上我已经被while循环搞疯6次了 能用for就用for:L
回复 使用道具 举报
kira 中级黑马 2014-1-22 12:06:43
9#
淡夜清风 发表于 2014-1-22 11:52
你第一个线程中的代码运行是非常快的,t2.start()时,t1都可能运行完了。
2000次太少了,要想看到交替显示 ...

原来如此 t1简直是一瞬就没了 有个新问题 我把t1的循环变为20000000次后 前面居然出现了null 这又是什么原因:'( 求教
回复 使用道具 举报
kira 发表于 2014-1-22 12:06
原来如此 t1简直是一瞬就没了 有个新问题 我把t1的循环变为20000000次后 前面居然出现了null 这又是什么 ...

老兄你的机器不行啊!!
我改成20000000后,是可以运行的。。而且也有交替。。

煤炭1....2吨
煤炭1....2吨
煤炭2....1吨
煤炭1....1吨
煤炭1....2吨
煤炭2....2吨
煤炭2....2吨
t1运行结束
煤炭2....2吨
煤炭2....2吨
煤炭2....2吨
煤炭2....2吨
煤炭2....2吨
这时候煤炭确定为+煤炭2.....2吨
煤炭2....2吨
煤炭2....2吨
煤炭2....2吨
煤炭2....2吨
煤炭2....2吨
回复 使用道具 举报
kira 中级黑马 2014-1-22 12:22:57
11#
淡夜清风 发表于 2014-1-22 12:20
老兄你的机器不行啊!!
我改成20000000后,是可以运行的。。而且也有交替。。

:'( 没办法 这单位的破电脑 卡的要死 话说出null那里 我已经找到原因了 是z那里循环数的问题
改小点就没有null了 感谢
回复 使用道具 举报
您需要登录后才可以回帖 登录 | 加入黑马