黑马程序员技术交流社区

标题: java基础-多线程-2 [打印本页]

作者: 914360849    时间: 2015-5-25 22:34
标题: java基础-多线程-2

多线程安全问题。

当多条语句在操作同一个线程共享数据时,一个线程对多条语句只执行了一部分,还没有执行完,另一个线程参与进来执行,导致共享数据的错误。

解决方法:对多条操作共享数据的语句,只能让一个线程都执行完;在执行过程中,其他线程不可以参与执行。

Java对于多线程的安全问题提供了专业的解决方式。就是同步代码块。

Synchronized(对象)

{ 需要被同步的代码;

}

对象如同锁,持有锁的线程可以在同步中执行。

没有持有锁的线程即使获取CPU执行权,也近不去,因为没有获取到锁。

经典例子:火车上的卫生间。

同步的前提:

1,  至少有两个线程。

2,  必须是多个线程使用同一个锁。

必须保证同步中只有一个线程在运行。

好处:解决了多线程的安全问题。

弊端:多个线程需要判断锁,较为消耗资源。

同步有两种表现形式:同步函数和同步代码块。

同步函数使用的是哪一个锁呢?

函数需要被对象调用,那么函数都有一个所属对象的引用:就是this。所以同步函数使用的锁是this。

多窗口同时买票:

class Ticket implements Runnable

{

         private   int tick=100;

         //Object obj =new Object();

         boolean flag=true;

         public  void run()

         {

                   if(flag)

                   {

                            while(true)

                            {

                                     synchronized(this)

                                     {

                                               if(tick >0)

                                               {

                                                        System.out.println(Thread.currentThread().getName()+" code: "+tick--);

                                               }

                                     }

                            }

                   }

                   else

                   {

                            while(true)

                                     show();

                   }

         }


         public synchronized void show()

         {

                   if(tick >0)

                            {

                                     System.out.println(Thread.currentThread().getName()+" ...show... "+tick--);

                            }

         }

}

class  TicketDemo2//ThisLockDemo

{

         public static void main(String[] args)

         {

                   Ticket t =new Ticket();

Thread t1=new Thread (t);//

                   Thread t2=new Thread (t);//

t1.start();

t.flag=false;

t2.start();

         }

}

当同步函数被静态修饰后,使用的锁是什么?

不是this,因为静态方法中不可以定义this。

静态进内存时,内存中没有本类对象,但是一定有该类对应的字节码文件对象。


静态的同步方法,使用的锁是该方法所在类的字节码文件对象。类名.class。


作者: 南方小道士    时间: 2015-5-25 22:51
路过看看
作者: 914360849    时间: 2015-5-25 23:00
欢迎 提问题,多多交流




欢迎光临 黑马程序员技术交流社区 (http://bbs.itheima.com/) 黑马程序员IT技术论坛 X3.2