您的位置:首页 > 职场人生

黑马程序员——多线程

2013-10-18 16:53 295 查看
----------------------
ASP.Net+Android+IO开发S、.Net培训、期待与您交流! ----------------------

线程



一个运行的程序就是一个进程,例如JVM一启动就有个java.exe的进程,一个进程里至少有一个线程,线程是一个独立的控制单元,控制着进程的运行。JVM启动就有一个叫main的线程,叫主线程。Java中对线程进行描叙的类有Thread类。



线程的创建

//继承Thread来创建线程,此时有三个进程,主线程和创建的两个线程

class Thread1 extends {
public void run(){
for(int x=0,x<10,x++){
System.out.println(x);
}
}
}

class ThreadTest{
public static void main(String[] args){
new Thread1().start;
new Thread1().start;
}
}

//这种继承方式创建线程后,Thread1就无法再去继承其他类了,这是一个局限性
//上面创建的两个线程都是分别独立运行的,如果要对共享数据进行操作,这种继承Thread类的方式就行不通了


//实现Runnable接口来创建线程
//通过实现Runnable接口可以实现多共享数据的多线程操作,同时实现它的子类也可以同时继承其他类

class Thread1 implements Runnable {
public void run(){
for(int x=0,x<10,x++){
System.out.println(x);
}
}
}

class ThreadTest{
public static void main(String[] args){
new Thread(new Thread1).start;
new Thread(new Thread1).start;
}
}

/*因为是实现接口的方式创建线程,所以如果run()方法中有异常出现的话只能在方法内进行捕获处理,不能在方法上声明抛出*/


同步中的安全问题


·同步问题


多个线程多共享数据操作时,一个线程对数据执行时可能会由于CPU的切换,另外一个线程进来,从而导致问题的发生。为了避免这种情况就要使用到同步代码块或同步函数。

synchronized(对象)

{

       需要被同步的代码 

}
同步函数是将synchronized关键字放在方法的返回值之前。

同步代码块里的对象就是一个同步锁,持有这个锁的线程才能进去,当它处于wait状态时会释放锁。

同步函数的锁是this锁,静态函数的锁是它所在的类的Class对象。



·死锁问题

 

class Test implements Runnable
{
private boolean flag;
Test(boolean flag)
{
this.flag = flag;
}

public void run()
{
if(flag)
{
while(true)
{
synchronized(MyLock.locka)
{
System.out.println(Thread.currentThread().getName()+"...if locka ");

/*t1线程想要到同步代码块中执行,但是lockb锁在t2线程里,t2还没释放*/
synchronized(MyLock.lockb)
{
System.out.println(Thread.currentThread().getName()+"..if lockb");
}
}
}
}
else
{
while(true)
{
synchronized(MyLock.lockb)
{
System.out.println(Thread.currentThread().getName()+"..else lockb");

/*t2线程想要到同步代码块中执行,但是locka锁在t1线程里,t1也还没释放,彼此都拿着对方的锁,形成死锁*/
synchronized(MyLock.locka)
{
System.out.println(Thread.currentThread().getName()+".....else locka");
}
}
}
}
}
}

class MyLock
{
static Object locka = new Object();
static Object lockb = new Object();
}

class  DeadLockTest
{
public static void main(String[] args)
{
Thread t1 = new Thread(new Test(true));
Thread t2 = new Thread(new Test(false));
t1.start();
t2.start();
}
}


 

 Lock接口



JDK1.5版本出现了更灵活的同步机制,就是使用Lock接口,它下面有个实现了Lock接口的ReentrantLock类,它有lock()和unlock()方法来替代同步代码块和同步函数,ReentrantLock里面的newCondition()方法创建出来的Condition对象里也拥有相应的线程通讯方法。它将Object中的wait(),notify(),notifyAll()方法都替换成Condition的await(),signal(),signalAll(),而且一个Lock锁上可以有多个Condition对象。



线程中的常见方法:



setDaemon(boolean):将线程标记为后台线程,后台线程和前台线程执行过程一样,但是当前台线程运行结束后,后台线程会自动结束。

join():等待该线程结束,当A线程执行到了B的join方法时,A就会处于冻结状态,当B运行结束后,A才具备运行资格,它可以完成对某个线程的临时加入执行。


----------------------
ASP.Net+Android+IOS开发、.Net培训、期待与您交流! ----------------------详细请查看:http://edu.csdn.net
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: