网易2015校招java岗多线程题

一个文件中有10000个数,用Java实现一个多线程程序将这个10000个数输出到5个不用文件中(不要求输出到每个文件中的数量相同)。要求启动10个线程,两两一组,分为5组。每组两个线程分别将文件中的奇数和偶数输出到该组对应的一个文件中,需要偶数线程每打印10个偶数以后,就将奇数线程打印10个奇数,如此交替进行。同时需要记录输出进度,每完成1000个数就在控制台中打印当前完成数量,并在所有线程结束后,在控制台打印”Done”.


试着写了一下,可以运行。代码如下:

package com.cn.edu.tju.thead;

import java.io.BufferedReader;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.Random;

public class TestFile {
	static int count = 0;// 记录线程读取的总数
	static Object object = new Object();// 修改10个线程中count值时的锁

	public static void main(String[] args) throws IOException {
		String file = "input.txt";
		inputFile(file);// 随机生成10000个数
		BufferedReader br = new BufferedReader(new FileReader(new File(file)));
		String s = br.readLine();
		br.close();
		String[] stringArray = s.split(" ");
		int index = 0;
		for (int i = 0; i < 5; i++) {
			int[] readArray = new int[2000];
			for (int j = 0; j < 2000; j++) {
				readArray[j] = Integer.parseInt(stringArray[index++]);
			}
			// 输出文件
			PrintWriter printWriter = new PrintWriter(new File("input"
					+ (i + 1) + ".txt"));
			Object objectPre = new Object();// 每组线程中的锁
			Even even = new Even();// 等待通知机制的条件
			Point point = new Point();// 记录当前偶数 奇数的位置
			PrintEvenFile printEvenFile = new PrintEvenFile(printWriter,
					readArray, objectPre, even, point);// 处理偶数
			PrintOddFile printOddFile = new PrintOddFile(printWriter,
					readArray, objectPre, even, point);// 处理奇数
			new Thread(printEvenFile).start();
			new Thread(printOddFile).start();
		}
	}

	// 随机生成10000个数
	static void inputFile(String name) {
		PrintWriter pw = null;
		try {
			pw = new PrintWriter(new File(name));
			Random random = new Random();
			for (int i = 0; i < 10000; i++) {
				int randomValue = random.nextInt(100);
				pw.append(randomValue + " ");
			}
			pw.close();
		} catch (FileNotFoundException e) {
			e.printStackTrace();
		}
	}

	// 等待通知机制的条件
	static class Even {
		boolean isEven = true;
	}

	// 记录当前偶数 奇数的位置
	static class Point {
		int evenPoint = 0;// 每组线程中偶数线程读取到的位置
		int oddPoint = 0;// //每组线程中奇数线程读取到的位置
	}

	// 处理偶数
	static class PrintEvenFile implements Runnable {
		PrintWriter printWriter = null;
		int[] readArray = null;
		Object lock = null;
		Even even = null;
		Point point = null;

		public PrintEvenFile(PrintWriter printWriter, int[] readArray,
				Object lock, Even even, Point point) {
			this.printWriter = printWriter;
			this.readArray = readArray;
			this.point = point;
			this.lock = lock;
			this.even = even;
		}

		@Override
		public void run() {
			while (readEvenFile()) {
			}
		}

		boolean readEvenFile() {
			synchronized (lock) {
				try {
					while (!even.isEven)
						lock.wait();
					for (int i = 0; i < 10;) {
						if (point.evenPoint >= 2000) {
							break;
						}
						if (readArray[point.evenPoint] % 2 == 0) {
							printWriter
									.append(readArray[point.evenPoint] + " ");
							printWriter.flush();
							i++;
							synchronized (object) {
								count++;
								if (count % 1000 == 0) {
									System.out.println("当前完成数量:" + count);
									if (count == 10000) {
										System.out.println("Done!");
									}
								}
							}
						}
						point.evenPoint = point.evenPoint + 1;
					}
					even.isEven = false;
					lock.notify();
					if (point.evenPoint >= 2000 && point.oddPoint >= 2000) {
						printWriter.close();
						return false;
					}
					return true;
				} catch (InterruptedException e) {
					e.printStackTrace();
				}
			}
			return true;
		}

	}

	// 处理奇数
	static class PrintOddFile implements Runnable {
		PrintWriter printWriter = null;
		int[] readArray = null;
		Object lock = null;
		Even even = null;
		Point point = null;

		public PrintOddFile(PrintWriter printWriter, int[] readArray,
				Object lock, Even even, Point point) {
			this.printWriter = printWriter;
			this.readArray = readArray;
			this.point = point;
			this.lock = lock;
			this.even = even;
		}

		@Override
		public void run() {
			while (readEvenFile()) {
			}
		}

		boolean readEvenFile() {
			synchronized (lock) {
				try {
					while (even.isEven)
						lock.wait();
					for (int i = 0; i < 10;) {
						if (point.oddPoint >= 2000) {
							break;
						}
						if (readArray[point.oddPoint] % 2 == 1) {
							printWriter.append(readArray[point.oddPoint] + " ");
							printWriter.flush();
							i++;
							synchronized (object) {
								count++;
								if (count % 1000 == 0) {
									System.out.println("当前完成数量:" + count);
									if (count == 10000) {
										System.out.println("Done!");
									}
								}
							}
						}
						point.oddPoint = point.oddPoint + 1;
					}
					even.isEven = true;
					lock.notify();
					if (point.evenPoint >= 2000 && point.oddPoint >= 2000) {
						printWriter.close();
						return false;
					}
					return true;
				} catch (InterruptedException e) {
					e.printStackTrace();
				}
			}
			return true;
		}
	}
}


  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值