线程 程序经常会遇到这样的情况:多个线程试图访问相同的资源,最终产生错误和不可预见的结果。
null
因此,需要通过某种同步方法确保在给定时间点只有一个线程可以访问资源。Java提供了一种使用同步块创建线程并同步其任务的方法。Java中的同步块用Synchronized关键字标记。Java中的同步块是在某个对象上同步的。同一对象上的所有同步块一次只能有一个线程在其中执行。试图进入同步块的所有其他线程都将被阻止,直到同步块内的线程退出该块。
以下是同步块的一般形式:
// Only one thread can execute at a time. // sync_object is a reference to an object// whose lock associates with the monitor. // The code is said to be synchronized on// the monitor objectsynchronized(sync_object){ // Access shared variables and other // shared resources}
这种同步是用Java实现的,有一个叫做监视器的概念。在给定的时间内,只有一个线程可以拥有一个监视器。当一个线程获得锁时,它就被称为进入了监视器。试图进入锁定监视器的所有其他线程将被挂起,直到第一个线程退出监视器。
下面是一个使用synchronized的多线程示例。
JAVA
// A Java program to demonstrate working of // synchronized. import java.io.*; import java.util.*; // A Class used to send a message class Sender { public void send(String msg) { System.out.println( "Sending " + msg ); try { Thread.sleep( 1000 ); } catch (Exception e) { System.out.println( "Thread interrupted." ); } System.out.println( "" + msg + "Sent" ); } } // Class for send a message using Threads class ThreadedSend extends Thread { private String msg; Sender sender; // Receives a message object and a string // message to be sent ThreadedSend(String m, Sender obj) { msg = m; sender = obj; } public void run() { // Only one thread can send a message // at a time. synchronized (sender) { // synchronizing the send object sender.send(msg); } } } // Driver class class SyncDemo { public static void main(String args[]) { Sender send = new Sender(); ThreadedSend S1 = new ThreadedSend( " Hi " , send ); ThreadedSend S2 = new ThreadedSend( " Bye " , send ); // Start two threads of ThreadedSend type S1.start(); S2.start(); // wait for threads to end try { S1.join(); S2.join(); } catch (Exception e) { System.out.println( "Interrupted" ); } } } |
输出
Sending Hi Hi SentSending Bye Bye Sent
每次运行程序时,输出都是相同的。
在上面的示例中,我们选择在ThreadedSend类的run()方法中同步Sender对象。或者,我们可以定义 整个send()块已同步 , 产生同样的结果。这样我们就不必在ThreadedSend类的run()方法中同步消息对象。
// An alternate implementation to demonstrate// that we can use synchronized with method also.class Sender { public synchronized void send(String msg) { System.out.println("Sending " + msg); try { Thread.sleep(1000); } catch (Exception e) { System.out.println("Thread interrupted."); } System.out.println("" + msg + "Sent"); }}
我们不必总是同步整个方法。有时它比 仅同步方法的一部分 .方法中的Java同步块使这成为可能。
// One more alternate implementation to demonstrate// that synchronized can be used with only a part of // methodclass Sender { public void send(String msg) { synchronized(this) { System.out.println("Sending " + msg ); try { Thread.sleep(1000); } catch (Exception e) { System.out.println("Thread interrupted."); } System.out.println("" + msg + "Sent"); } }}
本文由 苏拉迪普·巴鲁阿 。如果您发现任何不正确的地方,或者您想分享有关上述主题的更多信息,请发表评论
© 版权声明
文章版权归作者所有,未经允许请勿转载。
THE END