1_12JAVA练习

1. 双线程猜数字
用两个线程玩猜数字游戏,第一个线程负责随机给出1~10之间的一个整数,第二个线程负责猜出这个数。
要求:每当第二个线程给出自己的猜测后,第一个线程都会提示“猜小了”、“猜 大了”或“猜对了”。猜数之前,要求第二个线程要等待第一个线程设置好 要猜测的数。
第一个线程设置好猜测数之后,两个线程还要相互等待,其原 则是:第二个线程给出自己的猜测后,等待第一个线程给出的提示;
第一个 线程给出提示后,等待第二个线程给出猜测,如此进行,直到第二个线程给 出正确的猜测后,两个线程进入死亡状态。
 

import java.util.Map;

/**
 * 自定义随机数类
 */
public class RandomNum {
    private int randomNum ; // 随机数
    private int guessNum = 50 ;// 初始化猜测数
    // 表示线程的不同状态 wait(true)    notifyAll(false)
    private boolean flag = false ;
    // 表示猜测结果   1   表示 猜对了    0  表示 没猜对
    private int bigOrSmall ;
    private String msg ; // 提示信息

    // 构造方法  负责生成随机数
    public RandomNum() {
        randomNum = (int)(Math.random() * 100 + 1);
    }

    public int getRandomNum() {
        return randomNum;
    }

    public void setRandomNum(int randomNum) {
        this.randomNum = randomNum;
    }

    public int getGuessNum() {
        return guessNum;
    }

    public void setGuessNum(int guessNum) {
        this.guessNum = guessNum;
    }

    public boolean isFlag() {
        return flag;
    }

    public void setFlag(boolean flag) {
        this.flag = flag;
    }

    public int getBigOrSmall() {
        return bigOrSmall;
    }

    public void setBigOrSmall(int bigOrSmall) {
        this.bigOrSmall = bigOrSmall;
    }

    public String getMsg() {
        return msg;
    }

    public void setMsg(String msg) {
        this.msg = msg;
    }

    @Override
    public String toString() {
        return "RandomNum{" +
                "randomNum=" + randomNum +
                '}';
    }
}
import javax.crypto.spec.PSource;

/**
 * 线程1  负责生成随机数  并给出提示
 */
public class Thread1 implements Runnable{

    private RandomNum randomNum ;

    public Thread1(RandomNum randomNum) {
        this.randomNum = randomNum;
    }

    @Override
    public void run() {
        synchronized (Object.class){
            while (true){
                // true  表示wait  说明线程2正在猜数字 这里就继续等待
                if (randomNum.isFlag()){
                    try {
                        Object.class.wait();
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                }
                // 只有flag = false 的时候才会执行到这里
                // 开始判断线程2  是否猜对?
                if (randomNum.getGuessNum() < randomNum.getRandomNum()){
                    System.out.println("线程1===> 猜小了");
                    System.out.println("随机数===> " + randomNum.getRandomNum());
                    System.out.println("你猜的是===> " + randomNum.getGuessNum());
                    System.out.println("继续猜吧...");
                    // 设置参数
                    randomNum.setBigOrSmall(0); // 没猜对
                    randomNum.setFlag(true); //
                    Object.class.notifyAll(); //
                }else if (randomNum.getGuessNum() > randomNum.getRandomNum()){
                    System.out.println("线程1===> 猜大了");
                    System.out.println("随机数===> " + randomNum.getRandomNum());
                    System.out.println("你猜的是===> " + randomNum.getGuessNum());
                    System.out.println("继续猜吧...");
                    // 设置参数
                    randomNum.setBigOrSmall(0); // 没猜对
                    randomNum.setFlag(true); //
                    Object.class.notifyAll(); //
                }else {
                    System.out.println("线程1===> 猜对了");
                    System.out.println("随机数===> " + randomNum.getRandomNum());
                    System.out.println("你猜的是===> " + randomNum.getGuessNum());
                    randomNum.setBigOrSmall(1);
                    // 退出循环
                    break;
                }
            }


        }
    }
}
/**
 * 线程2  负责 猜数字
 */
public class Thread2 implements Runnable {

    private RandomNum randomNum ;

    public Thread2(RandomNum randomNum) {
        this.randomNum = randomNum;
    }

    @Override
    public void run() {
        synchronized (Object.class){
            int start = 1 ;
            int end = 100 ;
            while (randomNum.getBigOrSmall() == 0){
                if (randomNum.isFlag() == false){
                    try {
                        Object.class.wait();
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                }
                // flag = true 时 才会执行到这里
                // 使用二分法查找
                int mid = (start + end) / 2 ;
                if (mid == randomNum.getRandomNum()){
                    randomNum.setBigOrSmall(1); // 猜对了
                    randomNum.setGuessNum(mid);
                    Object.class.notifyAll();
                }else if (mid > randomNum.getRandomNum()){
                    randomNum.setGuessNum(mid);
                    end = mid - 1;
                    randomNum.setFlag(false);
                    Object.class.notifyAll();
                }else {
                    randomNum.setGuessNum(mid);
                    start = mid + 1;
                    randomNum.setFlag(false);
                    Object.class.notifyAll();
                }

                if (start > end){
                    randomNum.setMsg("没猜出来");
                }
            }
        }
    }
}
public class DoubleThreadGuessNum {
    public static void main(String[] args) {
        /**
         * 1. 双线程猜数字
         * 用两个线程玩猜数字游戏,第一个线程负责随机给出1~100之间的一个整数,第二个线程负责猜出这个数。
         * 要求:每当第二个线程给出自己的猜测后,第一个线程都会提示“猜小了”、“猜 大了”或“猜对了”。
         * 猜数之前,要求第二个线程要等待第一个线程设置好 要猜测的数。
         * 第一个线程设置好猜测数之后,两个线程还要相互等待,其原 则是:第二个线程给出自己的猜测后,等待第一个线程给出的提示;
         * 第一个 线程给出提示后,等待第二个线程给出猜测,如此进行,直到第二个线程给 出正确的猜测后,两个线程进入死亡状态。
         *
         * 如何获取线程状态?
         * wait()
         * notifyAll()
         * 两个线程  都需要随机数   线程1负责生成正确答案   线程2负责随机的去猜
         *
         * 共享的随机数类中  设置一些  结果提示“猜小了”、“猜大了”或“猜对了”
         *
         */

        RandomNum randomNum = new RandomNum();
        Thread1 thread1 = new Thread1(randomNum);
        Thread2 thread2 = new Thread2(randomNum);

        Thread t1 = new Thread(thread1);
        Thread t2 = new Thread(thread2);

        t1.start();
        t2.start();

    }
}

2. 写两个线程,一个线程打印1~52,另一个线程打印字母A~Z。打印顺序为12A34B56C........5152Z。要求用线程间的通信

public class PrintNum implements Runnable{
    @Override
    public void run() {
        synchronized (Object.class){
            for (int i = 1; i <= 52 ; i++) {
                // 12A34B56C78D
                System.out.print(i);
                if (i % 2 == 0 ){
                    Object.class.notifyAll();  // 叫醒别人
                    try {
                        Object.class.wait(); // 自己睡觉
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                }
            }
        }
    }
}

public class PrintZimu implements Runnable{
    @Override
    public void run() {
        synchronized (Object.class){
            for (char i = 'A'; i <= 'Z' ; i++) {
                System.out.print(i);
                Object.class.notifyAll();

                try {
                    Object.class.wait();
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        }
    }
}
public class PrintNumZimu {
    public static void main(String[] args) {
        /**
         * 2. 写两个线程,一个线程打印1~52,另一个线程打印字母A~Z。
         * 打印顺序为12A34B56C........5152Z。
         * 要求用线程间的通信
         */
        PrintNum printNum = new PrintNum();
        PrintZimu printZimu = new PrintZimu();

        Thread t1 = new Thread(printNum);
        Thread t2 = new Thread(printZimu);

        t1.start();
        t2.start();
    }
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值