黑马程序员_09. api-线程及单例设计模式

黑马程序员_api-线程及单例设计模式

a.明确以下概念:

1.进程:是一个正在执行中的程序。每一个进程执行都有一个执行顺序。该顺序是一个执行路径,或叫一个控制单元。

2.线程:就是进程中的一个独立的控制单元。线程在控制着进程的执行,一个进程中至少有一个线程。

3.多线程:如果一个进程中存在着多个控制单元,那么这个进程是一个多线程的应用程序。JVM启动时是一个多线程。

b.创建线程的两种方式

1. java已经提供了对线程这类事物的描述。就是Thread类。并且这个类把要运行的代码存放在了run方法中。所以可以自定义一个类,让它继承Thread类,覆写这个类的run方法,就可以了。步骤:

(1).定义类继承Thread。

(2).复写Thread类中的run方法。目的是将自定义代码存储在run方法。让线程运行。

(3).调用线程的start方法.该方法两个作用:启动线程,调用run方法。

需要注意的是,run方法是一个一般方法,它只用来存线程要运行的代码,start方法才能让线程运行。

	示例:
			class Demo extends Thread{
				public void run(){
					for(int x=0; x<100; x++)
						System.out.println("demo run----"+x);
				}
			}
			class ThreadDemo {
				public static void main(String[] args) {
					//创建好一个线程。
					Demo d = new Demo();
					//开启线程并执行该线程的run方法
					d.start();。
					//主线程运行的代码。
					for(int x=0; x<100; x++)
						System.out.println("Hello World!--"+x);
				}
			}

运行以上代码发现:自定义线程与主统一线程出现了随机运行的情况。这就是多线程的一个特性:随机性。谁抢到谁执行,至于执行多长,cpu说的算。发现自定义线程与主统一线程出现了随机运行的情况。这就是多线程的一个特性:随机性。谁抢到谁执行,至于执行多长,cpu说的算。要明确一点:在某一个时刻,只能有一个程序在运行(多核除外),cpu在做着快速的切换,看上去像是在同时运行一样。

2.通过观察发现Thread类的构造方法可以接收一个Runnable接口类型的对像,那么我们可以自定义一个类去实现这个接口,覆与这个接口的run方法,然后将这个对像作为实际参数传递给Thread类的构造函数即可。这样的操作避免了单继承的局限性。步骤:

(1).定义一个类实现Runnable接口,并覆写里面的run方法;

(2).创建Thread类的对像;

(3).将这个类的对像传递给Thread类的构函数;

(4).调用Thread对像的start方法。

<span style="white-space:pre">	</span>示例:
			//自定义一个类,实现Runnable接口,并覆写run方法。
			class Test implements Runnable{
				public void run(){
					for(int a=0; a<100; a++){
						System.out.println("Test--"+x);
					}
				}
			}
			class Thread_Runnable{
				public static void main(String[] args){
				//创建Thrread类的对像,将Test对像作传给Thread类的构造函数。
					Thread t = new Thread(new Test());
				//开启线程。
					t.start();
				}
			}

发现我们自定义类中的run方法被执行了!说明我们这样做也可以让线程帮我们运行我们自定义的代码。

c.关于线程的几个方法

(1).static Thread currentThread():获取当前线程对象;

(2).String getName(): 获取该线程名称;

(3).void setName(String name):设置该线程名称。

d.线程的5种状态:

(1).被创建;

(2).运行;

(3).临时状态(有执行资格但没有执行权);

(4).冻结(放弃了执行资格);

(5).消亡。

e.解决线程的安全问题

当一个线程对多条操作共享数据的代码执行的一部分。还没有执行完,另一个线程开始参与执行,这样容易出现安全隐患。在java中为解决这种安全隐患提供了专门的方案。如下介绍:

(1).同步函数

就是在函数的返回值前加上synchronized关键字,它持有的锁是this。

<span style="white-space:pre">	</span>定义示例:
			class Demo1{
				public synchronized void method(){
					System.out.println("我是同步函数。");
				}
			}

当同步函数用static修饰时

就是在synchronized前加上static关键字。静态的同步方法,使用的锁是该方法所在类的字节码文件对象, 类名.class。

<span style="white-space:pre">	</span>定义示例:
			class Demo2{
				public static synchronized void method(){
					System.out.println("我是用static修饰的同步函数。");
				}
			}

(2).同步代码块

就是对把需要同步的代码放在这个代码块当中,它使用的锁可以是任意对像。

格式:

synchronized(对像){

需要同步的代码;

}

(3).JDK1.5后对同步提供了显示的锁机制

它提供了多线程升级的解决方案,将同步Synchronized替换成现实Lock操作。将Object中的wait,notify notifyAll,替换了Condition对象。该对象可以Lock锁进行获取。在生产者、消费者的案例中实现了本方只唤醒对方的操作。

生产者、消费者示例代码:

class Resource
{
	private String name;
	private int count = 1;
	private boolean flag = false;	<span style="font-family: Arial, Helvetica, sans-serif;">	</span>
	private Lock lock = new ReentrantLock();
	private Condition condition_pro = lock.newCondition();
	private Condition condition_con = lock.newCondition();

	public  void set(String name)throws InterruptedException{
		lock.lock();
		try{
			while(flag)
				condition_pro.await();//t1,t2
			this.name = name+"--"+count++;

			System.out.println(Thread.currentThread().getName()+"-----生产者---"+this.name);
			flag = true;
			condition_con.signal();
		}
		finally{
<span style="white-space:pre">		</span><span style="font-family: Arial, Helvetica, sans-serif;">//释放锁的动作一定要执行。</span>
			lock.unlock();
		}
	}

	public  void out()throws InterruptedException{
		lock.lock();
		try{
			while(!flag)
				condition_con.await();
			System.out.println(Thread.currentThread().getName()+"----消费者----"+this.name);
			flag = false;
			condition_pro.signal();
		}
		finally{
			lock.unlock();
		}

	}
}

class Producer implements Runnable
{
	private Resource res;
	Producer(Resource res){
		this.res = res;
	}
	public void run(){
		while(true){
			try{
				res.set("+商品+");
			}
			catch (InterruptedException e){
<span style="white-space:pre">				</span><span style="font-family: Arial, Helvetica, sans-serif;">//只为演示代码,省略处理方式。</span>
<span style="white-space:pre">				</span>e.<span style="font-family: Arial, Helvetica, sans-serif;"><strong>printstackTrace();</strong></span><span style="white-space:pre">
</span>			}
		}
	}
}

class Consumer implements Runnable{
	private Resource res<span style="font-family: Arial, Helvetica, sans-serif;">;</span>
	Consumer(Resource res){
		this.res = res;
	}
	public void run(){
		while(true){
			try{
				res.out();
			}
			catch (InterruptedException e){
<span style="white-space:pre">				</span><span style="font-family: Arial, Helvetica, sans-serif;">//只为演示代码,省略处理方式。</span>
<span style="font-family:Arial, Helvetica, sans-serif;"><span style="white-space:pre">								</span>e.</span><strong>printStackTrace</strong>
			}
		}
	}
}

f.单例设计模式

模式就是在日常生活中人们实践过程中总结出来的,用来解决问题最行之有效的方法,它满足了人们复杂的业务需求。java中总的一共有23总设计模式。单例设计模式就是其中一种,解决了一个类在内存中只存在一个对像。

单例设计模式分为两种,都分为以下三步:

步骤:

a.将构造函数私有化;

b.在类中建立一个静态并私有的对像;

c.对外提供公共一个方法可以获取到该对像。

<span style="white-space:pre">		</span>(1).饿汉式

			示例:
			class Single{
				private Single(){}
				private static Single s = new Single();
				public static s getInstance(){
					return s;
				}
			}
		(2).懒汉式
			懒汉式也称作类的延时加载,是方法被调用时对像才初始化。
			示例:
			class Single{
				private Single(){}
				private Single s = null;
				public void static s getInstance(){
					if(s==null){
						synchronized(Single.class){
							if(s==null){
								s = new Single();
							}
						}
					}
					return s;
				}
			}

时间: 2024-12-28 00:28:41

黑马程序员_09. api-线程及单例设计模式的相关文章

线程安全问题-单例设计模式

第一种:饿汉式单例设计模式 在类加载的时候就创建好了一个静态的对象供系统使用,以后不再改变,所以天生就是线程安全的. 但是初始化就占用了系统的资源. package thread; /* * 饿汉式单例模式:饿汉式在类一创建的时候就已经创建好了一个静态的对象供系统使用,以后不再改变,所以天生就是线程安全的 */ class Singleton3{ private Singleton3(){ } private static final Singleton3 INSTANCE = new Sing

黑马程序员——经典C语言程序设计100例

1.数字排列 2.奖金分配问题 3.已知条件求解整数 4.输入日期判断第几天 5.输入整数进行排序 6.用*号显示字母C的图案 7.显示特殊图案 8.打印九九口诀 9.输出国际象棋棋盘 10.打印楼梯并按条件打印笑脸 11.经典兔子问题 12.判断素数 13.水仙花数问题 14.正整数分解质因数 15.学习成绩划分 16.正整数求其最大公约数和最小公倍数 17.统计英文字母/空格/数字个数 18.求s=a+aa+aaa+aa...a的值 19.求解"完数" 20.球体自由落下物理问题

黑马程序员__多线程

------<a href="http://www.itheima.com" target="blank">Java培训.Android培训.iOS培训..Net培训</a>.期待与您交流! ------- 1.线程是程序执行的一条路径, 一个进程中可以包含多条线程,多线程并发执行可以提高程序的效率, 可以同时完成多项工作. 2.开启新线程的两种方式 1).继承Thread [java] view plaincopy public stati

Java设计模式之一 单例设计模式

1.什么叫设计模式: 设计模式的概念首先来源于其它行业:建筑业,在早起建房子的时候,肯定是经验缺乏.显得杂乱无序的,这就会造成很多问题,在行业发展过程,通过不断的经验积累,前辈们针对这些问题提出了合理解决方案,这就是设计模式,参照设计模式往往可以解决很多问题,在计算机编程方面,也会出现类似问题,所以牛人们把这些解决问题的方案进行归类和总结,形成了面向对象编程的23种设计模式. 2.单例模式(特点): Java中单例模式定义:"一个类有且仅有一个实例,并且自行实例化向整个系统提供."通过

【黑马】程序员————多线程(二)单例设计模式、线程间通信,JDK1.5互斥锁

------Java培训.Android培训.iOS培训..Net培训.期待与您交流!----- 一.单例设计模式 单例设计模式的意义: A.保证类在内存中只有一个对象,不提供外部访问方式,构造函数用private修饰. B.提供公共方法(static修饰,类的静态方法),获取类的实例.单例设计模式分为饿汉和懒汉两种模式. 饿汉式&懒汉式 class Test33 { public static void main(String[] args) { Fanjianan.getInstance()

黑马程序员——【Java基础】——泛型、Utilities工具类、其他对象API

一.泛型 (一)泛型概述 1.泛型:JDK1.5版本以后出现的新特性,用于解决安全问题,是一个类型安全机制. 2.泛型技术是给编译器使用的技术,用于编译时期,确保类型的安全. 3.泛型的擦除:运行时,会将泛型去掉,生成class文件中的是不带泛型的,这个称为“泛型的擦除”.擦除泛型的原因是为了兼容运行时的类加载器. 4.泛型的好处:(1)将运行时期出现的问题ClassCastException,转移到了编译时期.方便于程序员解决问题,让运行时期问题减少.安全.(2)避免了强制转换的麻烦. 5.泛

黑马程序员--单例设计模式

单例设计模式:解决的问题:保证一个类在内存中的对象唯一性.比如:多程序读取一个配置文件时,建议配置文件封装成对象.会方便操作其中数据,又要保证多个程序读到的是同一个配置文件对象,就需要该配置文件对象在内存中是唯一的. Runtime()方法就是单例设计模式进行设计的. 如何保证对象唯一性呢?思想:1,不让其他程序创建该类对象.2,在本类中创建一个本类对象.3,对外提供方法,让其他程序获取这个对象. 步骤:1,因为创建对象都需要构造函数初始化,只要将本类中的构造函数私有化,其他程序就无法再创建该类

黑马程序员--Java基础学习笔记【单例设计模式、网络编程、反射】

------Java培训.Android培训.iOS培训..Net培训.期待与您交流! ------- 设计模式分类: 创建模式:是对类的实例化过程的抽象化,又分为类创建模式和对象创建模式 类创建模式:工厂方法模式 对象-:简单工厂(静态工厂方法)模式.抽象工厂模式.单例模式.建造模式- 结构模式:描述如何将类或者对象结合在一起形成更大的结构 适配器模式.缺省模式.合成模式.装饰模式(包装模式).门面模式- 行为模式:对不同的对象之间划分责任和算法的抽象化 不变模式.策略模式.迭代子模式.命令模

黑马程序员——Java基础---单例

------<a href="http://www.itheima.com" target="blank">Java培训.Android培训.iOS培训..Net培训</a>.期待与您交流!                                         单例 设计模式:解决问题最行之有效的方法,让问题简单化,Java中有23种. 单例:解决一个类在内存,只有一个对象 想要保证对象唯一: 1,为了避免其他程序过多建立该类对象,