5-3的一些问题 为什么在 实现runnable类种方法的语句打印输出也会是随机的,而非确定的

5-3的一些问题 为什么在 实现runnable类种方法的语句打印输出也会是随机的,而非确定的

老师,您好,我在天气类的作业中,添加了 一句输出语句,打印输出这是第几次读天气/生成天气。 这些输出语句也是位置不确定的。想知道是为什么吖。

下面是我的作业的完整代码和输出

Weather 类

package com.imooc.thread;

import java.util.Random;

public class Weather {

	private int temperature;
	private int humidity;
	private boolean flag = false;// True to read

	// Constructor
	public Weather() {
		// TODO Auto-generated constructor stub
	}

	public Weather(int temp, int humidity) {
		this.setHumidity(humidity);
		this.setTemperature(temp);
	}

	// Getters and Setters

	public int getTemperature() {
		return temperature;
	}

	public void setTemperature(int temperature) {
		this.temperature = temperature;
	}

	public int getHumidity() {
		return humidity;
	}

	public void setHumidity(int humidity) {
		this.humidity = humidity;
	}

	public boolean isFlag() {
		return flag;
	}

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

	@Override
	public String toString() {
		return "Weather data [temperature=" + temperature + ", humidity=" + humidity + "]";
	}

	// Methods (read and generate methods must be synchronized)
	// They can not be interrupted by other when one thread calls them
	public synchronized void read() {
		if(this.flag) {
			//if it is the time to read the weather read them 
			System.out.println("read Weather feature : " + this.toString());
			//update the flag and notify other thread. 
			flag = false; 
			this.notifyAll();
		}else {
			try {
				this.wait();
			} catch (InterruptedException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
	}

	public void generate() {
		synchronized (this) {
			if(!this.flag) {
				Random random = new Random();
				this.setHumidity(random.nextInt(41));
				this.setTemperature(random.nextInt(101));
				System.out.println("Generate Weather feature : " + this.toString());
				//After generate weather, modify the flag and notify other threads 
				this.setFlag(true);
				this.notifyAll();
			}else {
				//if this time is not to generate weather, releases the lock on the object 
				// so that another thread can jump in and acquire a lock.
				try {
					this.wait();
				} catch (InterruptedException e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
				}
			}
		}
		
	}

}

两个实现runnable 接口的类 

package com.imooc.thread;

public class GenerateWeather implements Runnable {
	private Weather weather;
	public GenerateWeather() {
		// TODO Auto-generated constructor stub
	}

	public GenerateWeather(Weather weather) {
		super();
		this.setWeather(weather);
	}

	public Weather getWeather() {
		return weather;
	}

	public void setWeather(Weather weather) {
		this.weather = weather;
	}

	@Override
	public void run() {
		// TODO Auto-generated method stub
		for(int i = 0; i<100; i++) {			
			weather.generate();
			System.out.println("第"+i+ "次写");
			try {
				Thread.sleep(100);
			} catch (InterruptedException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
	}
	

}
package com.imooc.thread;

public class ReadWeather implements Runnable {
	private Weather weather;


	public ReadWeather() {
		// TODO Auto-generated constructor stub
	}

	public ReadWeather(Weather weather) {
		super();
		this.weather = weather;
	}

	public Weather getWeather() {
		return weather;
	}

	public void setWeather(Weather weather) {
		this.weather = weather;
	}

	@Override
	public void run() {
		// TODO Auto-generated method stub
		for(int i = 0; i<100 ; i++) {			
			weather.read();
			System.out.println("第"+i+ "次读");
			try {
				Thread.sleep(100);
			} catch (InterruptedException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}

	}

}

测试代码及输出:

package com.imooc.thread;

public class WeatherTest {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		Weather weather = new Weather();
		Thread readWeather = new Thread(new ReadWeather(weather));
		Thread geneWeather = new Thread(new GenerateWeather(weather));
		readWeather.start();
		geneWeather.start();

	}

}

输出:

Generate Weather feature : Weather data [temperature=56, humidity=2]

第0次读

第0次写

read Weather feature : Weather data [temperature=56, humidity=2]

第1次写

第1次读

Generate Weather feature : Weather data [temperature=32, humidity=34]

第2次写

第2次读

read Weather feature : Weather data [temperature=32, humidity=34]

第3次读

Generate Weather feature : Weather data [temperature=59, humidity=19]

第3次写

read Weather feature : Weather data [temperature=59, humidity=19]

Generate Weather feature : Weather data [temperature=86, humidity=35]

第4次写

第4次读

read Weather feature : Weather data [temperature=86, humidity=35]

第5次读

Generate Weather feature : Weather data [temperature=70, humidity=19]

第5次写

read Weather feature : Weather data [temperature=70, humidity=19]

第6次写

第6次读

Generate Weather feature : Weather data [temperature=32, humidity=29]

第7次读

第7次写

read Weather feature : Weather data [temperature=32, humidity=29]

第8次写

第8次读

Generate Weather feature : Weather data [temperature=4, humidity=5]

第9次读


正在回答

登陆购买课程后可参与讨论,去登陆

2回答

两个线程的执行顺序就是随机的。但作业要求是,你增加逻辑代码后,不要让它随机,让它固定下来。先产生天气数据再读取天气数据。所以你看你加了flag后Generate Weather feature :与read Weather feature顺序是固定的。你无法固定线程顺序,但你可以固定线程中某代码的执行顺序呀,这不就达到目的了嘛。祝:学习愉快

提问者 慕斯6088333 2018-12-30 15:00:50

BTY,  本次课程中(例题和作业)的死锁产生的条件是不是 环路等待条件的一个实例,读和写都放弃了对对象的锁。(都释放了资源)但同时都在等待对方取得资源。 (A等待B 释放资源, B也在等在A释放资源)。 所以通过规定顺序, 先读再写,或者先写再读,这样避免了死锁~??谢谢啦

  • 产生死锁是因为,A拿着一个B需要的资源,B拿着一个A需要的资源,两个人谁也不放手,你等我,我等你所以死锁了。"通过规定顺序, 先读再写,或者先写再读,这样避免了死锁"也可以避免死锁,但更多的是利用逻辑代码来控制。而作业中规定顺序是为了模拟现实情况,你得先产生天气情况,再读取天气数据呀。
    2018-12-31 11:57:30
问题已解决,确定采纳
还有疑问,暂不采纳

恭喜解决一个难题,获得1积分~

来为老师/同学的回答评分吧

0 星
请稍等 ...
意见反馈 帮助中心 APP下载
官方微信

在线咨询

领取优惠

免费试听

领取大纲

扫描二维码,添加
你的专属老师