张祥祥老师的线程类学习

一、练习一:
public classs Test extends Thread{
private TestDo testDo;
private String key;
private String value;

public Test(String key,String key2,String value){
    this.testDo = TestDo.getInstance();
    this.key = key+key2;
    this.value = value;
}

public static void main(String [] str){
    Test a = new Test("1","","1");
    Test b = new Test("1","","2");
    Test c = new Test("3","","3");
    Test d = new Test("4","","4");
    System.out.println("begin:"+(System.currentTimeMillis()/1000));
    //启动线程
    a.start();
    b.start();
    c.start();
    d.start();
}

public void run(){
    testDo.doSome(key,value);
}

}

class TestDo{
private TestDo(){}
private static TestDo _instance = new TestDo();
public static TestDo getInstance(){
return _instance;
}

private CopyOnWriteArrayList keys = new CopyOnWriteArrayList();
public void doSome(Object key,String value){
    Object o = key;
    if(!keys.contains(o)){
        keys.add(o);
    }else{
        for(Iterator iter = keys.iterator();iter.hasNext()){
            Object oo = iter.next();
            if(oo.equals(o)){
                o==oo;
            }
        }
    }

    synchronized(o){
        Thread.sleep(1000);
        System.out.println(key+":"+value + ":"
                    + (System.currentTimeMillis() / 1000));
    }
}

}

二、练习二:
public class Test{
public static void main(String [] str){
final BlockingQueue queue = new ArrayBlockingQueue(1);
for(int i=0;i<4;i++){
new Thread(new Runnable(){
public void run(){
while(true){
String log = queue.take();
parseLog(log);
}
}
}).start();
}

    System.out.println("begin:"+(System.currentTimeMillis()/1000));
    /*模拟处理16行日志,下面的代码产生了16个日志对象,当前代码需要运行16秒才能打印完这些日志。
    修改程序代码,开四个线程让这16个对象在4秒钟打完。
    */
    for(int i=0;i<16;i++){
        final String log=""+(i+1);
        {
            queue.put(log);;
        }
    }
}

public static void parseLog(String log){
    System.out.println(log+":"+(System.currentTimeMillis()/1000));
    Thread.sleep(1000);
}

}

三、练习三:queue
public class Test{
public static void main(String [] str){
final Semaphore semaphore = new Semaphore(1);
final SynchronousQueue queue = new SynchronousQueue();
for(int i=0;i<10;i++){
new Thread(new Runnable(){
public void run(){
semaphore.acquire();
String input = queue.take();
String output = TestDo.doSome(input);
System.out.println(output);
System.out.println(Thread.currentThread().getName()+ “:”+output);
semaphore.release();
}
}).start();
}

    System.out.println("begin:"+(System.currentTimeMillis()/1000));
    for(int i=0;i<10;i++){
        String input = i+"";
        queue.put(input);
    }
}

}

class TestDo{
public static String doSome(String input){
Thread.sleep(1000);
String output = input + “:”+ (System.currentTimeMillis() / 1000);
return output;
}
}

四、练习四:定时器练习Timer
public class TraditionalTimerTest{
private static int count = 0;
public static void main(String [] str){
/*new Timer().schedule(new TimerTask(){
public void run(){
System.out.println(“boming!!!”);
}
},1000,3000);*/

    class MyTimerTask extends TimerTask{
        public void run(){
            count = (count+1)%2;
            System.out.println("boming!!!!!!!");
            new Timer().schedule(new MyTimerTask(),2000+2000*count);
        }
    }

    new Timer().schedule(new MyTimerTask(),2000);

    while(true){
        System.out.println(new Date().getSeconds());
        Thread.sleep(1000);
    }
}

}

五、练习五:Synchronized练习实现线程互斥
public class TraditionalThreadSynchronized{
public static void main(String str []){
new TraditionalThreadSynchronized().init();
}

private void init(){
    final Outputer outputer = new Outputer();;
    new Thread(new Runnable(){
        public void run(){
            while(true){
                Thread.sleep(10);
                outputer.output("zhangxiaoxiang");
            }
        }
    }).start();


    new Thread(new Runnable(){
        public void run(){
            while(true){
                Thread.sleep(10);
                outputer.output3("lihuoming");
            }
        }
    }).start();
}


static class Outputer{
    public void output(String name){
        int len = name.length();
        synchronized(Outputer.class){
            for(int i = 0; i < len; i ++){
                System.out.print(name.charAt(i));
            }
            System.out.println();
        }
    }

    public synchronized void output2(String name){
        int len = name.length();
        for(int i=0;i<len;i++){
            System.out.print(name.charAt(i));
        }
        System.out.println();
    }

    public static synchronized void output3(String name){
        int len = name.length();
        for(int i=0;i<len;i++){
            System.out.print(name.charAt(i));
        }
        System.out.println();
    }
}

}

六、练习六:wait,notify,synchronized实现线程通信
public class TraditionalThreadCommunication{
public static void main(String [] str){
final Business business = new Business();
//子线程
new Thread(new Runnable(){
public void run(){
for(int i=1;i<=50;i++){
business.sub(i);
}
}
}).start();

    //主线程
    for(int i=1;i<=50;i++){
        business.main(i);
    }
}

}

class Business{
private boolean bShouldSub = true;
public synchronized void sub(int i){
while(!bShouldSub){
this.wait();
}
for(int j=1;j<=10;j++){
System.out.println(“sub thread sequence of ” + j + “,loop of ” + i);
}
bShouldSub = false;
this.notify();
}

public synchronized void main(int i){
    while(bShouldSub){
        //等待,让其它线程运行
        this.wait();
    }
    for(int j=1;j<=100;j++){
        System.out.println("main thread sequence of " + j + ",loop of " + i);
    }
    bShouldSub = true;
    //将其它线程唤醒
    this.notify();
}

}

练习七:传统线程的创建:Thread
public class TraditionalThread{
public static void main(String [] str){
//方式一
Thread thread = new Thread(){
public void run(){
while(true){
Thread.sleep(5000);
System.out.println(“1:” + Thread.currentThread().getName());
System.out.println(“2:” + this.getName());
}
}
};
thread.start();

    //方式二:
    Thread thread2 = new Thread(new Runnable(){
        public void run(){
            Thread.sleep(5000);
            System.out.println("1:" + Thread.currentThread().getName());
        }
    });
    thread2.start();


    new Thread(new Runnable(){
        public void run(){

        }
    }).start();
}

}

八:练习八:Condition实现线程间通信,结合ReentrantLock使用
public class ThreeConditionCommunication{
public static void main(String [] str){
final Business business = new Business();
//子线程1
new Thread(new Runnable(){
public void run(){
for(int i=1;i<=50;i++){
business.sub2(i);
}
}
}).start();

    //子线程2
    new Thread(new Runnable(){
        for(int i = 1; i <= 50; i++){
            business.sub3(i);
        }
    }).start();

    //主线程
    for(int i=1;i<=50;i++){
        business.main(i);
    }
}


static class Business{
    Lock lock = new ReentrantLock();
    Condition condition1 = new lock.newCondition();
    Condition condition2 = new lock.newCondition();
    Condition condition3 = new lock.newCondition();
    private int shouldSub = 1;

    //方法2:sub2
    public void sub2(int i){
        lock.lock();
        while(shouldSub != 2){
        try{
            condition2.await();
        }
        for(int j=1;j<=10;j++){
            System.out.println("sub2 thread sequence of " + j + ",loop of " + i);
        }
        shouldSub = 3;
        condition3.signal();
        }finally{
            lock.unlock();
        }
    }

    //方法3:sub3
    public void sub3(int i){
        lock.lock();
          try{
              while(shouldSub != 3){
                  try {
                    condition3.await();
                } catch (Exception e) {
                    e.printStackTrace();
                }
              }
                for(int j=1;j<=20;j++){
                    System.out.println("sub3 thread sequence of " + j + ",loop of " + i);
                }
              shouldSub = 1;
              condition1.signal();
          }finally{
              lock.unlock();
          }
    }

    //主方法
    public  void main(int i){
          lock.lock();
          try{
             while(shouldSub != 1){
                    try {
                        condition1.await();
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                }
                for(int j=1;j<=100;j++){
                    System.out.println("main thread sequence of " + j + ",loop of " + i);
                }
                shouldSub = 2;
                condition2.signal();
      }finally{
          lock.unlock();
      }
}

}

练习九:线程池的使用:ExecutorService、Executors
public class ThreadPoolTest{
public static void main(String [] str){
ExecutorService threadPool = Executors.newFixedThreadPool(3);
ExecutorService threadPool = Executors.newCachhedThreadPool();
ExecutorService threadPool = Executors.newSingleThreadExecutor();
for(int i=1;i<=10;i++){
final int task = i;
threadPool.execute(new Runnable(){
public void run(){
for(int j=1;j<=10;j++){
Thread.sleep(20);
System.out.println(Thread.currentThread().getName() + ” is looping of ” + j + ” for task of ” + task);
}
}
});
}

    System.out.println("all of 10 tasks have committed! ");


    //线程池的定时任务Executors.newScheduledThreadPool(3).scheduleAtFixedRate
    Executors.newScheduledThreadPool(3).scheduleAtFixedRate(new Runnable(){
        public void run(){
            System.out.println("bombing!!!");
        }
    },6,2,TimeUnit.SECONDS);
}

}

练习十:Semaphore实现线程同步,相当于wait、notify
public class SemaphoreTest{
public static void main(String [] str){
ExecutorService service = Executors.newCachedThreadPool();
final Semaphore sp = new Semaphore(3);
for(int i=0;i<10;i++){
Runnable runnable = new Runnable(){
public void run(){
try {
sp.acquire();
} catch (InterruptedException e1) {
e1.printStackTrace();
}
System.out.println(“线程” + Thread.currentThread().getName() +
“进入,当前已有” + (3-sp.availablePermits()) + “个并发”);
try {
Thread.sleep((long)(Math.random()*10000));
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println(“线程” + Thread.currentThread().getName() +
“即将离开”);
sp.release();
//下面代码有时候执行不准确,因为其没有和上面的代码合成原子单元
System.out.println(“线程” + Thread.currentThread().getName() +
“已离开,当前已有” + (3-sp.availablePermits()) + “个并发”);
}
};
service.execute(runnable);
}
}

练习十一:Exchanger练习
public class ExchangerTest{
public static void main(String [] str){
ExecutorService service = Executors.newCachedThreadPool();
final Exchanger exchanger = new Exchanger();
service.execute(new Runnable(){
public void run(){
String data1 = “zxx”;
System.out.println(“线程” + Thread.currentThread().getName() +
“正在把数据” + data1 +”换出去”);
Thread.sleep((long)(Math.random()*10000));
String data2 = (String)exchanger.exchange(data1);
System.out.println(“线程” + Thread.currentThread().getName() +
“换回的数据为” + data2);
}
});

    service.execute(new Runnable(){
        public void run() {
            try {               

                String data1 = "lhm";
                System.out.println("线程" + Thread.currentThread().getName() + 
                "正在把数据" + data1 +"换出去");
                Thread.sleep((long)(Math.random()*10000));                  
                String data2 = (String)exchanger.exchange(data1);
                System.out.println("线程" + Thread.currentThread().getName() + 
                "换回的数据为" + data2);
            }catch(Exception e){

            }               
        }   
    });     
}

}

练习十二:CyclicBarrier练习
public class CyclicBarrierTest {

public static void main(String[] args) {
    ExecutorService service = Executors.newCachedThreadPool();
    final  CyclicBarrier cb = new CyclicBarrier(3);
    for(int i=0;i<3;i++){
        Runnable runnable = new Runnable(){
            public void run(){
            try {
                Thread.sleep((long)(Math.random()*10000));  
                System.out.println("线程" + Thread.currentThread().getName() + 
                        "即将到达集合地点1,当前已有" + (cb.getNumberWaiting()+1) + "个已经到达," + (cb.getNumberWaiting()==2?"都到齐了,继续走啊":"正在等候"));                       
                cb.await();

                Thread.sleep((long)(Math.random()*10000));  
                System.out.println("线程" + Thread.currentThread().getName() + 
                        "即将到达集合地点2,当前已有" + (cb.getNumberWaiting()+1) + "个已经到达," + (cb.getNumberWaiting()==2?"都到齐了,继续走啊":"正在等候"));
                cb.await(); 
                Thread.sleep((long)(Math.random()*10000));  
                System.out.println("线程" + Thread.currentThread().getName() + 
                        "即将到达集合地点3,当前已有" + (cb.getNumberWaiting() + 1) + "个已经到达," + (cb.getNumberWaiting()==2?"都到齐了,继续走啊":"正在等候"));                     
                cb.await();                     
            } catch (Exception e) {
                e.printStackTrace();
            }               
            }
        };
        service.execute(runnable);
    }
    service.shutdown();
}

}

练习十三:CountdownLatch
public class CountdownLatchTest {

public static void main(String[] args) {
    ExecutorService service = Executors.newCachedThreadPool();
    final CountDownLatch cdOrder = new CountDownLatch(1);
    final CountDownLatch cdAnswer = new CountDownLatch(1);      
    for(int i=0;i<3;i++){
        Runnable runnable = new Runnable(){
                public void run(){
                try {
                    System.out.println("线程" + Thread.currentThread().getName() + 
                            "正准备接受命令");                     
                    cdOrder.await();
                    System.out.println("线程" + Thread.currentThread().getName() + 
                    "已接受命令");                               
                    Thread.sleep((long)(Math.random()*10000));  
                    System.out.println("线程" + Thread.currentThread().getName() + 
                            "回应命令处理结果");                        
                    cdAnswer.countDown();                       
                } catch (Exception e) {
                    e.printStackTrace();
                }               
            }
        };
        service.execute(runnable);
    }       
    try {
        Thread.sleep((long)(Math.random()*10000));

        System.out.println("线程" + Thread.currentThread().getName() + 
                "即将发布命令");                      
        cdOrder.countDown();
        System.out.println("线程" + Thread.currentThread().getName() + 
        "已发送命令,正在等待结果");    
        cdAnswer.await();
        System.out.println("线程" + Thread.currentThread().getName() + 
        "已收到所有响应结果");   
    } catch (Exception e) {
        e.printStackTrace();
    }               
    service.shutdown();
}

}

十四:练习十四:CallableAndFuture
public class CallableAndFuture{
public static void main(String [] str){
ExecutorService threadPool = Executors.newSingleThreadExecutor();
Future future = threadPool.submit(
new Callable(){
public String call() throws Exception{
Thread.sleep(2000);
return “hello”;
}
}
);

    System.out.println("等待结果!!!!");
    System.out.println("拿到结果:"+future.get());


    ExecutorService threadPool2 =  Executors.newFixedThreadPool(10);
    CompletionService<Integer> completionService = new ExecutorCompletionService<Integer>(threadPool2);
    for(int i=1;i<=10;i++){
        final int seq = i;
        completionService.submit(new Callable<Integer>(){
            public Integer call() throws Exception{
                Thread.sleep(new Random().nextInt(5000));
                return seq;
            }
        });
    }

    for(int i = 0;i<10;i++){
        System.out.println(
                    completionService.take().get());
    }
}

}

十五、使用线程的读写锁实现一个缓存类:
public class CacheDemo {

private Map<String, Object> cache = new HashMap<String, Object>();
public static void main(String[] args) {

}

private ReadWriteLock rwl = new ReentrantReadWriteLock();
public  Object getData(String key){
    rwl.readLock().lock();
    Object value = null;
    try{
        value = cache.get(key);
        if(value == null){
            rwl.readLock().unlock();
            rwl.writeLock().lock();
            try{
                if(value==null){
                    value = "aaaa";//查询数据库
                }
            }finally{
                rwl.writeLock().unlock();
            }
            rwl.readLock().lock();
        }
    }finally{
        rwl.readLock().unlock();
    }
    return value;
}

}

十六:练习十六:BlockingQueue队列的使用:
public class BlockingQueueTest {
@SuppressWarnings(“all”)
public static void main(String[] args) {
final BlockingQueue queue = new ArrayBlockingQueue(3);
for(int i=0;i<2;i++){
new Thread(){
public void run(){
while(true){
try {
Thread.sleep((long)(Math.random()*1000));
System.out.println(Thread.currentThread().getName() + “准备放数据!”);
queue.put(1);
System.out.println(Thread.currentThread().getName() + “已经放了数据,” +
“队列目前有” + queue.size() + “个数据”);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}.start();
}

    new Thread(){
        public void run(){
            while(true){
                try {
                    //将此处的睡眠时间分别改为100和1000,观察运行结果
                    Thread.sleep(1000);
                    System.out.println(Thread.currentThread().getName() + "准备取数据!");
                    queue.take();
                    System.out.println(Thread.currentThread().getName() + "已经取走数据," +                           
                            "队列目前有" + queue.size() + "个数据");                    
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        }
    }.start();          
}

}

十七:BlockingQueue队列的通信
public class BlockingQueueCommunication {
public static void main(String[] args) {

    final Business business = new Business();
    new Thread(
            new Runnable() {
                @Override
                public void run() {

                    for(int i=1;i<=50;i++){
                        business.sub(i);
                    }

                }
            }
    ).start();

    for(int i=1;i<=50;i++){
        business.main(i);
    }

}

 static class Business {

      BlockingQueue<Integer> queue1 = new ArrayBlockingQueue<Integer>(1);
      BlockingQueue<Integer> queue2 = new ArrayBlockingQueue<Integer>(1);

      {

// Collections.synchronizedMap(null);
try {
System.out.println(“xxxxxdfsdsafdsa”);
queue2.put(1);
} catch (InterruptedException e) {
e.printStackTrace();
}
}

      public  void sub(int i){
            try {
                queue1.put(1);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            for(int j=1;j<=10;j++){
                System.out.println("sub thread sequece of " + j + ",loop of " + i);
            }
            try {
                queue2.take();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
      }

      public  void main(int i){
            try {
                queue2.put(1);
            } catch (InterruptedException e1) {
                e1.printStackTrace();
            }
            for(int j=1;j<=100;j++){
                System.out.println("main thread sequece of " + j + ",loop of " + i);
            }
            try {
                queue1.take();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
      }
  }

}

猜你喜欢

转载自blog.csdn.net/jay_888/article/details/82663704