您的位置:首页 > 编程语言 > Java开发

java并发编程——共享资源的操作

2015-07-18 11:40 543 查看
一、并发编程产生的问题

并发编程给程序的设计带来的巨大的好处,但多线程的出现也同样带来了一些问题。

因为线程执行的时间是不确定的,所以,当不同的线程共同访问某一共享资源的时候,可以对共享资源的操作产生错误。

比如:有一共享资源整型num,如果有几个线程同时对其做减1操作。假设当num=90时,线程一对其做减一操作,其从内存中取出num=90,然后到cpu进行减法操作。

这个时候,线程一挂起,线程二开始执行,线程二从内存中取出num=90,对其进行减一操作,num变为了89,。而线程切换到线程一的时候,线程一继续执行,在cpu中做减法操作,num变为89。

也就是执行了两次减一操作,当时共享资源num只是从90变为了89.

二、如何解决这一问题——互斥量操作

1、为了保护资源,采用了加锁的方式。当资源被一个任务使用的时候,对其进行加锁操作。只用当前任务完成,才释放锁。下一个任务才能访问该资源。

在java中使用synchronized关键字的形式控制资源的访问。

2、共享资源。在java中共享资源一般是以对象的形式存在内存片段的。但也可以是文件,输入输出端口,或者是打印机。

3、synchronized的使用

(1)将方法标记为synchronized,如果某个任务处于一个标记为synchroenized的方法的调用中,那么在这个线程从该方法返回之前,其他所有要调用类中任何标记为synchronized方法的线程都会被阻塞。

(2)临界区

有时,希望防止多个线程同时访问方法内部的部分代码,而不是防止访问整个方法。

通过这种方法,分离出来的代码段称为临界区,它使用synchronized关键字建立。

synchronized被用来指定某个对象,此对象的锁被用来对花括号内的代码进行同步控制。

synchronized(对象)

{

需要控制的代码!

}

这种方法叫做同步控制块,通过同步控制块,而不是对整个方法进行同步控制,可以使得多个任务访问对象的时间性能得到显著提高。

使用一对象,作为锁

package com.xiancheng;

class task1 implements Runnable
{

private int num = 100;
Object o = new Object();
public  void run()
{
while(num>0)
{
synchronized(o)
{

if(num>0)
{
try
{
Thread.sleep(10);
}
catch(InterruptedException e)
{

}

System.out.println(Thread.currentThread().getName()+"........"+num--);
}
}
}
}

}

class task2 implements Runnable
{

private int num = 100;
//	Object o = new Object();
public  void run()
{
while(num>0)
{
synchronized(this)
{

if(num>0)
{
try
{
Thread.sleep(10);
}
catch(InterruptedException e)
{

}

System.out.println(Thread.currentThread().getName()+"........"+num--);
}
}
}
}

}
class task2 implements Runnable
{

public void run()
{

for(int z=0;z<=10;z++)
{
for(int y=0;y<=99999999;y++){}
System.out.println(Thread.currentThread().getName()+"....z="+z);
}
}

}

public class hello {
public static void main(String[] args){

task1 t1= new task1();
task2 t2 = new task2();
Thread nt1 = new Thread(t1);
Thread nt2 = new Thread(t1);
Thread nt3 = new Thread(t1);
nt1.start();
nt2.start();
nt3.start();

}

}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: