`
dysfzhoulong
  • 浏览: 70440 次
  • 性别: Icon_minigender_1
  • 来自: 长沙市
社区版块
存档分类
最新评论

java多线程

阅读更多
1. 创建线程的两种方式
2. 线程的生命周期
3. 同步的方式
4. 死锁
5. 生产消费模型、监控模型

创建线程的两种方式
public class Thread1 extends Thread {
	private int j;

	// 重写run方法
	public void run() {
		for (; j < 100; j++) {
			System.out.println(getName() + " " + j);
		}
	}

	// 主函数
	public static void main(String args[]) {
		for (int i = 0; i < 100; i++) {
			// 打印主线程执行信息
			System.out.println(Thread.currentThread().getName() + " " + i);
			if (i == 20) {
				// 新启两个线程
				new Thread1().start();
				new Thread1().start();
			}
		}
	}
}
public class Thread2 implements Runnable {

	private int j;

	// 实现run方法
	public void run() {
		for (; j < 100; j++) {
			System.out.println(Thread.currentThread().getName() + " " + j);
		}
	}

	// 主方法
	public static void main(String args[]) {
		
		for (int i = 0; i < 100; i++) {
			// 打印主线程执行信息
			System.out.println(Thread.currentThread().getName() + " " + i);
			if (i == 20) {
				// 新启两个线程
				Thread2 thread=new Thread2();
				new Thread(thread,"新线程1").start();
				new Thread(thread,"新线程2").start();
			}
		}
	}
}

结果:



从图片上我们可以看到,第一张图片数据之间没有实现共享,但是第二张图片,我们可以看到线程1和线程2共享了线程类的实例属性,这是因为程序所创建的Runnable对象只是线程的的target,而多个线程可以共享一个target;
对于用继承Thread和实现Runnable,采用Runnable的话该实现类还可以进行继承,扩展性更强;
启动一个线程用的是start(),而不是run();如果直接用run()则会将它当作一个普通的方法来使用;用start(),则会将run方法当作线程执行体来处理;
前面的两个示例,实际上至少有三条线程,主线程和程序显示创建的两条线程;主线程的线程执行体不是由run方法来确定的,而是由main方法来确定的

线程的生命周期
当程序用new关键字创建一个线程之后,该线程就处于新建状态,此时它和其它Java对象一样,仅仅由Java虚拟机为其分配内存,并初始化了其成员变量的值。当线程调用了start方法后,该线程处于就绪状态;


同步的方式
一.synchronized关键字保证同步
    锁定方法:表示这个方法同时只能被一个线程访问
//同步方法 同步监视器为this
	public synchronized int getM1(int count){
		return 1;
	}

锁定对象:表示其限定的代码块只能同时被一个线程访问
//同步代码块
	public void getM2(){
		synchronized(obj){
			//代码块,obj为同步监视器
		}
	}

二.新用JDK1.5新的同步机制
private Lock lock=new ReentrantLock();
	//在方法内使用同步锁
	public void getM3(){
		//开始锁
		lock.lock();
		//同步区。。。
		try{
			
		}finally{
			//释放锁
			lock.unlock();
		}
		
	}

死锁
当两线程相互等待对方释放同步监视器时就会出现死锁,一旦出现死锁,整个程序既不会发生任何的异常,也不会给出任何的提示,只是所有线程处理阻塞状态,无法继续
class A {
	synchronized void foo(B b) {
		String name = Thread.currentThread().getName();

		System.out.println(name + " entered A.foo");

		try {
			Thread.sleep(1000);
		} catch (Exception e) {
			System.out.println("A Interrupted");
		}

		System.out.println(name + " trying to call B.last()");
		// 因为b对象被锁住了,调用b内的方法时,在等锁的释放
		b.last();
	}

	synchronized void last() {
		System.out.println("Inside A.last");
	}
}

class B {
	synchronized void bar(A a) {
		String name = Thread.currentThread().getName();
		System.out.println(name + " entered B.bar");

		try {
			Thread.sleep(1000);
		} catch (Exception e) {
			System.out.println("B Interrupted");
		}

		System.out.println(name + " trying to call A.last()");
		// 因为a对象被锁住了,调用a内的方法时,在等锁的释放
		a.last();
	}

	synchronized void last() {
		System.out.println("Inside A.last");
	}
}

class Deadlock implements Runnable {
	A a = new A();

	B b = new B();

	Deadlock() {
		Thread.currentThread().setName("MainThread");
		Thread t = new Thread(this, "RacingThread");
		t.start();

		a.foo(b); // 同步监视器为a
		System.out.println("Back in main thread");
	}

	public void run() {
		b.bar(a); // 同步监视器为b
		System.out.println("Back in other thread");
	}

	public static void main(String args[]) {
		new Deadlock();
	}
}

生产消费模型、监控模型
//生产消费模型
public class Main {
	public static void main(String args[]) {
		List<Egg> list = new ArrayList<Egg>();
		new Product(list).start();
		new Customer(list).start();
	}
}public class Egg {
	private int id;
	private String name;

	public int getId() {
		return id;
	}

	public void setId(int id) {
		this.id = id;
	}

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public String toString() {
		return id + " " + name;
	}

}public class Product extends Thread {
	private List<Egg> list;
	private int count;

	public Product(List<Egg> list) {
		this.list = list;
	}

	// 重写run方法
	public void run() {
		System.out.println("生产线程启动");
		while (true) {
			try {
				Thread.sleep(100);
				synchronized (list) {
					//还有鸡蛋时
					while (list.size() > 0) {
                          list.wait();
					}
					//没有鸡蛋时
					while(list.size()==0){
						Egg egg=new Egg();
						egg.setId(count++);
						egg.setName("鸡蛋");
						System.out.println("生产线程生产"+egg.toString());
						list.add(egg);
						//通知消费线程
						list.notify();
					}
				}
			} catch (InterruptedException e) {
				e.printStackTrace();
			}
		}
	}
}public class Customer extends Thread {
	private List<Egg> list;

	public Customer(List<Egg> list) {
		this.list = list;
	}
	// 重写run方法
	public void run() {
		System.out.println("消费线程启动");
		while (true) {
			try {
				Thread.sleep(100);
				synchronized (list) {
					//没有则等待
					while (list.size() == 0) {
                         list.wait(); 
					}
					//有鸡蛋时
					while(list.size()>0){
						
						System.out.println("消费线程消费"+list.remove(0).toString());
						//通知生产线程
						list.notify();
					}
				}
			} catch (InterruptedException e) {
				e.printStackTrace();
			}
		}

	}
}

//监控模型public class Control implements Runnable {
	// 存放统计线程的队列
	private static List<CountFile> list = new ArrayList<CountFile>();

	// 主函数
	public static void main(String args[]) {
		// 取得系统的根目录个数
		java.io.File[] dirF = java.io.File.listRoots();
		// 根据目录创建统计纯种个数
		for (int i = 0; i < dirF.length; i++) {
			CountFile cf = new CountFile(dirF[i].getAbsolutePath());
			cf.start();
			list.add(cf);
		}
		System.out.println(dirF.length + " 个统计线程已启动");
		// 启动监视线程
		new Thread(new Control()).start();
		System.out.println("监视线程已启动");
	}

	// 实现run方法
	public void run() {
		boolean flag = true;
		String result = "";
		while (flag) {
			for (int i = 0; i < list.size(); i++) {
				if (list.get(i).isFinished()) {
					// 取得统计结果
					result += list.get(i).getResult();
					// 移出统计完的线程
					list.remove(i);
				}
			}
			// 全部统计完
			if (list.isEmpty()) {
				flag = false;
			}
			try {
				Thread.sleep(1000);
			} catch (Exception e) {
				e.printStackTrace();
			}
		}
		System.out.println("统计结果如下:");
		System.out.println(result);
	}
}public class CountFile extends Thread {
	private String root;// 进行搜索的根目录的名字
	private int lengthCount;// 所有文件长度
	private int dirCount;// 目录数
	private int realFileCount;// 统计的真正文件数量
	private boolean finished = false;

	// 构造时传入搜索根目录名
	public CountFile(String root) {
		this.root = root;
	}

	/**
	 * 查看线程是否统计结束
	 * 
	 * @return
	 */
	public boolean isFinished() {
		return finished;
	}

	/**
	 * 返回统计结果
	 * 
	 * @return
	 */
	public String getResult() {
		StringBuffer result = new StringBuffer();
		result.append(root + "盘统计结果如下:\r\n");
		result.append("  文件数量: " + realFileCount);
		result.append("   目录数: " + dirCount);
		result.append("   文件总长度(单位K): " + lengthCount / 1204);
		result.append("\r\n");
		return result.toString();
	}

	// 重写run方法
	public void run() {
		long start = System.currentTimeMillis();
		lengthCount = countProcess(root);
		long cost = System.currentTimeMillis() - start;
		finished = true;
	}

	/**
	 * 统计目录下文件的长度
	 * 
	 * @param root
	 *            要统计的目录
	 * @return 目录下文件的长度
	 */
	private int countProcess(String root) {
		int count = 0;
		File dirFile = new File(root);
		// 目录不存在
		if (!dirFile.exists()) {
			return count;
		}
		// 获得目录下的所有文件组成的数组
		File[] subFile = dirFile.listFiles();
		if (subFile == null) {
			return count;
		}
		// 对这个数组进行遍历
		for (int i = 0; i < subFile.length; i++) {
			// 是个目录
			if (subFile[i].isDirectory()) {
				dirCount++;
				count += countProcess(subFile[i].getAbsolutePath());// 用递归计算该目录下的文件长度
			}
			// 是一个文件
			if (subFile[i].isFile()) {
				realFileCount++;
				count += subFile[i].length();
			}
		}
		return count;
	}
}
  • 大小: 4.9 KB
  • 大小: 5.7 KB
  • 大小: 37.9 KB
1
3
分享到:
评论

相关推荐

    Java多线程知识点总结

    Java多线程是Java编程语言中一个非常重要的概念,它允许开发者在一个程序中创建多个执行线程并行运行,以提高程序的执行效率和响应速度。在Java中,线程的生命周期包含五个基本状态,分别是新建状态(New)、就绪...

    java 多线程操作数据库

    ### Java多线程操作数据库:深入解析与应用 在当今高度并发的应用环境中,Java多线程技术被广泛应用于处理数据库操作,以提升系统的响应速度和处理能力。本文将基于一个具体的Java多线程操作数据库的应用程序,深入...

    Java多线程设计模式上传文件

    Java多线程设计模式上传文件Java多线程设计模式上传文件Java多线程设计模式上传文件Java多线程设计模式上传文件Java多线程设计模式上传文件Java多线程设计模式上传文件Java多线程设计模式上传文件Java多线程设计模式...

    java多线程经典案例

    Java多线程是Java编程中的重要概念,它允许程序同时执行多个任务,极大地提升了程序的效率和性能。在Java中,实现多线程有两种主要方式:通过实现Runnable接口或者继承Thread类。本案例将深入探讨Java多线程中的关键...

    java多线程Demo

    Java多线程是Java编程中的一个重要概念,它允许程序同时执行多个任务,提高了程序的效率和响应速度。在Java中,实现多线程有两种主要方式:继承Thread类和实现Runnable接口。 1. 继承Thread类: 当我们创建一个新...

    java多线程的讲解和实战

    Java多线程是Java编程中的重要概念,尤其在如今的多核处理器环境下,理解并熟练掌握多线程技术对于提高程序性能和响应速度至关重要。本资料详细讲解了Java多线程的原理,并提供了丰富的实战代码,非常适合Java初学者...

    java多线程分页查询

    ### Java多线程分页查询知识点详解 #### 一、背景与需求分析 在实际的软件开发过程中,尤其是在处理大量数据时,如何高效地进行数据查询成为了一个关键问题。例如,在一个用户众多的社交平台上,当用户需要查看...

    java多线程ppt

    java多线程PPT 多线程基本概念 创建线程的方式 线程的挂起与唤醒 多线程问题

    java多线程读取文件

    Java多线程读大文件 java多线程写文件:多线程往队列中写入数据

    Java多线程机制(讲述java里面与多线程有关的函数)

    Java多线程机制是Java编程中至关重要的一部分,它允许程序同时执行多个任务,提升应用程序的效率和响应性。以下是对各个知识点的详细说明: 9.1 Java中的线程: Java程序中的线程是在操作系统级别的线程基础上进行...

    深入浅出 Java 多线程.pdf

    在本文中,我们将深入浅出Java多线程编程的世界,探索多线程编程的基本概念、多线程编程的优点、多线程编程的缺点、多线程编程的应用场景、多线程编程的实现方法等内容。 一、多线程编程的基本概念 多线程编程是指...

    java 多线程并发实例

    在Java编程中,多线程并发是提升程序执行效率、充分利用多核处理器资源的重要手段。本文将基于"java 多线程并发实例"这个主题,深入探讨Java中的多线程并发概念及其应用。 首先,我们要了解Java中的线程。线程是...

    JAVAJAVA多线程教学演示系统论文

    《JAVA多线程教学演示系统》是一篇深入探讨JAVA多线程编程的论文,它针对教育领域中的教学需求,提供了一种生动、直观的演示方式,帮助学生更好地理解和掌握多线程技术。这篇论文的核心内容可能包括以下几个方面: ...

    java多线程实现大批量数据导入源码

    本项目以"java多线程实现大批量数据导入源码"为题,旨在通过多线程策略将大量数据切分,并进行并行处理,以提高数据处理速度。 首先,我们需要理解Java中的线程机制。Java通过`Thread`类来创建和管理线程。每个线程...

    汪文君JAVA多线程编程实战(完整不加密)

    《汪文君JAVA多线程编程实战》是一本专注于Java多线程编程的实战教程,由知名讲师汪文君倾力打造。这本书旨在帮助Java开发者深入理解和熟练掌握多线程编程技术,提升软件开发的效率和质量。在Java平台中,多线程是...

    java多线程查询数据库

    综上所述,"java多线程查询数据库"是一个涉及多线程技术、线程池管理、并发控制、分页查询等多个方面的复杂问题。通过理解和掌握这些知识点,我们可以有效地提高数据库操作的效率和系统的响应速度。

    java 多线程编程实战指南(核心 + 设计模式 完整版)

    《Java多线程编程实战指南》这本书深入浅出地讲解了Java多线程的核心概念和实战技巧,分为核心篇和设计模式篇,旨在帮助开发者掌握并应用多线程技术。 1. **线程基础** - **线程的创建**:Java提供了两种创建线程...

    java多线程,对多线程,线程池进行封装,方便使用

    Java多线程是Java编程中的重要概念,它允许程序同时执行多个任务,提高了程序的效率和响应速度。在Java中,我们可以通过实现Runnable接口或继承Thread类来创建线程。然而,直接使用线程可能存在一些问题,如资源管理...

    JAVA多线程编程技术PDF

    这份“JAVA多线程编程技术PDF”是学习和掌握这一领域的经典资料,涵盖了多线程的全部知识点。 首先,多线程的核心概念包括线程的创建与启动。在Java中,可以通过实现Runnable接口或继承Thread类来创建线程。创建后...

    Java多线程编程核心技术_完整版_java_

    Java多线程编程是Java开发中的重要组成部分,它允许程序同时执行多个任务,极大地提高了程序的效率和响应性。在Java中,多线程主要通过继承Thread类或实现Runnable接口来实现。本教程《Java多线程编程核心技术》将...

Global site tag (gtag.js) - Google Analytics