/**
 * Wicket类,用于模拟售票点
 */
public class Wicket implements Runnable{
 private int tickets=100; //共一百张票
 public void run(){
  while(true){
   if(tickets>0){
    try
    {
     Thread.sleep(10); //令当前线程暂停10毫秒
    }
    catch (Exception e)
    {
     System.out.println(e.getMessage());
    }
    
    System.out.println(Thread.currentThread().getName()+
         " is saling ticket "+tickets--);
   }
  }
 }
 public static void main(String[] agrs){
  Runnable runnable=new Wicket(); //创建资源对象
  /**
   * 创建四个线程,共享资源对象
   */
  new Thread(runnable).start();
  new Thread(runnable).start();
  new Thread(runnable).start();
  new Thread(runnable).start();
 }
}


/**
 * ThreadDemo类,用于调度线程
 */
public class ThreadDemo{
 public static void main(String[] agrs)throws Exception{
  ThreadTest thread1=new ThreadTest("block");
  new Thread(thread1).start();
  Thread.sleep(1);
  thread1.setInvokeFlag("method");
  new Thread(thread1).start();
 }
}
class ThreadTest implements Runnable{
 private String str;
 private int tickets=100;
 public ThreadTest(String str){
  this.str=str;
 }
 public void setInvokeFlag(String flag){
  this.str=flag;
 }
 public void run(){  
  if(str.equals("method")){
   while(true){
    sale();
   }
  }
  else{
   while(true){
    /**
     * 同步代码块,以对象本身作为监视器
     */
    synchronized(this){
     if(tickets>0){
      try{
       Thread.sleep(10);
      }
      catch (Exception e){
       System.out.println(e);
      }
      System.out.println(Thread.currentThread().getName()+
       " is saling ticket "+tickets--);
     }
    }
   }
  }
 }
 /**
  * 同步方法,以对象本身作为监视器
  */
 private synchronized void sale(){
  if(tickets>0){
   try{
    Thread.sleep(10);
   }
   catch (Exception e){
    System.out.println(e);
   }
   System.out.println(Thread.currentThread().getName()+
    " is saling ticket "+tickets--);
  }
 }
}

/**
 * DeadLock类,用于调度线程和制造死锁
 */
public class DeadLock implements Runnable{
 private A a=new A();
 private B b=new B();
 public DeadLock()throws Exception{
  Thread.currentThread().setName("Main Thread");
  new Thread(this).start();
  a.foo(b);
 }
 public void run(){
  Thread.currentThread().setName("Racing Thread");
  try{
   b.bar(a);
  }
  catch (Exception e){
   System.out.println(e);
  }
  
 }
 public static void main(String[] agrs)throws Exception{
  new DeadLock();
 }
}
class A{
 public synchronized void foo(B b) throws Exception{
  String threadName=Thread.currentThread().getName();
  System.out.println(threadName);
  Thread.sleep(10);
  System.out.println(threadName+" trying to call B.last()");
  b.last();
 }
 public synchronized void last(){
  System.out.println("inside A.last()");
 }
}
class B{
 public synchronized void bar(A a) throws Exception{
  String threadName=Thread.currentThread().getName();
  System.out.println(threadName);
  Thread.sleep(10);
  System.out.println(threadName+" trying to call A.last()");
  a.last();
 }
 public synchronized void last(){
  System.out.println("inside B.last()");
 }
}


/**
 * Q类用于存储数据
 */
class Q{
 private String name;
 private String sex;
 public synchronized void put(String name,String sex){
  this.name=name;
  this.sex=sex;
 }
 public synchronized String get(){
  return name+"---->"+sex;
 }
}
/**
 * 生产者类
 */
class Producer implements Runnable{
 private Q q;
 public Producer(Q q){
  this.q=q;
 }
 public void run(){
  int i=0;
  while(true){
   if(i==0){
    q.put("张飞","男");
   }
   else{
    q.put("貂蝉","女");
   }
   i=(i+1)%2;
  }
 }
}
/**
 * 消费者类
 */
class Consumer implements Runnable{
 private Q q;
 public Consumer(Q q){
  this.q=q;
 }
 public void run(){
  while(true){
   System.out.println(q.get());
  }
 }
}
/**
 * 程序的主调用类
 */
public class ThreadCommunation{
 public static void main(String[] agrs){
  Q q=new Q();
  Thread t1=new Thread(new Producer(q));
  Thread t2=new Thread(new Consumer(q));
  t1.start();
  t2.start();
 }
}


/**
 * Q类用于存储数据
 */
class Q{
 private String name;
 private String sex;
 private boolean flag=false; //表示存储空间的状态
 public synchronized void put(String name,String sex){
  if(flag){
   try{
    wait(); //令当前线程放弃监视器并进入等待状态
   }
   catch (Exception e){
    System.out.println(e);
   } 
  }
  this.name=name;
  this.sex=sex;
  flag=true;
  notify(); //释放与监视器相关联的第一个等待线程,令其回到可运行状态
 }
 public synchronized String get(){
  if(!flag){
   try{
    wait(); //令当前线程放弃监视器并进入等待状态
   }
   catch (Exception e){
    System.out.println(e);
   }
   
  }
  flag=false;
  notify(); //释放与监视器相关联的第一个等待线程,令其回到可运行状态
  return name+"---->"+sex;
 }
}
/**
 * 生产者类
 */
class Producer implements Runnable{
 private Q q;
 public Producer(Q q){
  this.q=q;
 }
 public void run(){
  int i=0;
  while(true){
   if(i==0){
    q.put("张飞","男");
   }
   else{
    q.put("貂蝉","女");
   }
   i=(i+1)%2;
  }
 }
}
/**
 * 消费者类
 */
class Consumer implements Runnable{
 private Q q;
 public Consumer(Q q){
  this.q=q;
 }
 public void run(){
  while(true){
   System.out.println(q.get());
  }
 }
}
/**
 * 程序的主调用类
 */
public class ThreadCommunation{
 public static void main(String[] agrs){
  Q q=new Q();
  Thread t1=new Thread(new Producer(q));
  Thread t2=new Thread(new Consumer(q));
  t1.start();
  t2.start();
 }
}