`
hellsing42
  • 浏览: 263693 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

java线程同步问题

阅读更多
一般,有3种使用锁进行同步的方法
    a.方法同步,例如public synchronized void xxx()...
    b.静态方法同步,例如public static synchronized void xxx()...
    c.程序块同步,例如
        ...
        synchronized(object oLock)    //注意:object不一定是该类的实例
        {
            ...
        }
   
    在用法a中,当某线程执行方法xxx时,jvm会锁定该类的实例,直到方法xxx执行完毕。执行xxx的过程看看成是这样的:
    *请求得到类实例的实例锁,假如有其他线程在执行,则等待;
    *得到实例锁,执行xxx;
    *执行完毕,释放实例锁;
    注意,这个过程是jvm完成的,我们只需要把某个对象方法声明为synchronized即可,实例锁可以理解为实例本身。
   

在用法b中,当某线程执行静态方法xxx时,也是有jvm控制经过以上的3个步骤,所不同的是由于此时不存在类实例(静态方法嘛),所

以用法a中实例锁被实例的类的锁取代,其实对我们编程来讲,几乎没有任何区别,我们只需要把静态方法声明为synchronized即可。
    在用法c中,oLock可以被理解为一个传接棒,它可以是任何类的实例,当某个线程试图访问声明为synchronized的程序块的时候,jvm

判断oLock是否被锁定,假如没有被锁定,则锁定oLock并执行该程序块。执行完毕释放该锁。
    在对象级使用锁(实例锁)通常是一种比较粗糙的方法,设想一下,假如一个对象可能去访问N个共享资源,那么假如有一个线程独占

了该对象,而仅仅是为了使用其中的一项资源的话,也会造成想访问其它资源的线程也处于堵塞状态。用程序块同步可以很好解决这个问题,

以下是使用被称为Fine_Grain_Lock的例子,看,效果是不是很high:
            class FineGrainLock {
                   MyMemberClass x, y;
                Object xlock = new Object(), ylock = new Object();
                public void foo() {
                      synchronized(xlock) {
                              //access x here
                          }
                          //do something here - but don't use shared resources
                           synchronized(ylock) {
                             //access y here
                          }
                   }

                  public void bar() {
                          synchronized(this) {
                             //access both x and y here
                          }
                      //do something here - but don't use shared resources
                   }
            }

2.notify/wait/notifyAll,上面是交给jvm使用同步方法处理共享资源问题,可以理解为抢占型的共享资源解决方案,而使用

notify/wait/notifyall可以在程序中控制对共享资源的访问,实现一种合作型的共享资源解决方案。一个小例子:
    //WNNa:wait/notify/notifyAll
    public class WNNa implements Runnable
    {
        private static Object oLock = new Object();
        public void run()
        {
          try
          {
            synchronized(oLock)
            {
                TwoBoy t = (TwoBoy)Thread.currentThread();
                if(t.getName() == "Mike")
                {
                    oLock.wait();
                    t.eat();
                    oLock.notify();
                    oLock.wait();
                    t.drink();
                }
                else
                {
                    t.eat();
                    oLock.notify();
                    oLock.wait();
                    t.drink();
                    oLock.notify();
                }    
            }
          }
          catch(Exception ex)
          {
            System.out.println("Error in synchronized:" + ex.getMessage());
          }
        }
        public WNNa()
        {
            TwoBoy t1 = new TwoBoy(this,"Tom");
            TwoBoy t2 = new TwoBoy(this,"Mike");
            t1.start();
            t2.start();
        }
        public static void main(String argv[])
        {
            new WNNa();
        }
    }
    
    class TwoBoy extends Thread
    {
        private String strName = "";
        public TwoBoy(Runnable t,String name)
        {
            super(t,name);
            strName = name;
        }
        public void drink()
        {
            System.out.println(strName + " drink!");        
        }
        public void eat()
        {
            System.out.println(strName + " eat!");
        }    
    }

    在上面的例子中,我们可以控制线程按照业务逻辑运行,而非简单的排它的使用共享资源的问题了。
3.信号量方案:在有N个共享资源而有M个线程的情况下(M>>N),需要用到信号量。信号量代表可用资源的数目,线程需要使用资源时首先判

断是否有足够的资源,没有的话等待,直到其它线程释放资源为止,得到资源后,信号量应减去该线程使用的资源数目,待这些资源使用完毕

,线程应释放这些资源。
    class Semaphore {
           private int count;
           public Semaphore(int n) {
                  this.count = n;
           }

           public synchronized void acquire() {
                  while(count == 0) {
                     try {
                            wait();
                     } catch (InterruptedException e) {
                            //keep trying
                     }
                  }
                  count--;
           }
    
           public synchronized void release() {
                  count++;
                  notify(); //alert a thread that's blocking on this semaphore
           }
    }
分享到:
评论

相关推荐

    java 线程同步 信号量控制同步

    这些机制可以用于解决不同类型的线程同步问题。 线程同步机制的选择取决于具体的应用场景和需求。开发者需要根据实际情况选择合适的线程同步机制,以确保程序的正确性和效率。 线程同步机制是 Java 编程中的一种...

    java线程同步java线程同步

    java线程同步java线程同步java线程同步

    Java多线程同步论文.doc

    Java多线程同步是Java编程中至关重要的一部分,特别是在并发编程领域。Java提供了多种同步机制来确保线程安全,防止数据不一致性和竞态条件。在Java中,synchronized关键字是实现线程同步的关键,它提供了互斥访问,...

    java线程同步详解

    总结一下,Java线程同步的关键点: 1. **线程同步是为了解决共享资源的并发访问问题,防止数据不一致和冲突。** 2. **同步意味着线程排队,依次访问共享资源,而不是同时访问。** 3. **只有共享变量(可变状态)才...

    Java多线程同步.pdf

    因此,在使用Java多线程同步机制时,需要小心避免这些问题的出现。 Java多线程同步机制在实际应用中的应用 Java多线程同步机制在实际应用中有很多应用,例如: * 在线银行系统中,使用Java多线程同步机制来确保...

    JAVA 线程实现数据库的主从同步更新

    在Java编程环境中,...总之,使用Java线程实现数据库主从同步更新是一种常见且实用的技术手段,它涉及到多线程编程、数据库操作、事务管理等多个方面。理解和掌握这些知识点对于开发高可用性的分布式系统至关重要。

    Java 线程同步调用

    Java线程同步调用是多线程编程中的基石,它通过同步方法和同步代码块两种方式,有效地控制了线程之间的交互,防止了多线程环境下常见的并发问题。无论是对于初学者还是有经验的开发者,掌握和熟练应用这些同步机制都...

    java线程同步及通信

    Java线程同步与通信是多线程编程中的关键概念,用于解决并发访问共享资源时可能出现的数据不一致性和竞态条件问题。以下将详细介绍这两个主题,以及如何通过代码示例进行演示。 1. **线程同步**: 线程同步是确保...

    java多线程同步例子

    java多线程同步互斥访问实例,对于初学者或是温故而知新的同道中人都是一个很好的学习资料

    JAVA实现线程间同步与互斥生产者消费者问题

    在Java编程中,线程同步和互斥是多线程编程中的重要概念,它们用于解决多个线程同时访问共享资源时可能出现的问题。本项目通过一个生产者消费者问题的实例,展示了如何在Java中实现线程间的同步与互斥。 生产者消费...

    java多线程同步问题

    多线程注意:wait()方法的调用要有判定条件常用 while () obj.wait(timeout, nanos); ... // Perform action appropriate to condition } synchronized会影响共享数据,但对其他语句的执行不会有规律了!

    操作系统实验 多线程同步与互斥 java编写 有界面

    在“操作系统实验 多线程同步与互斥 java编写 有界面”的实验中,可能需要设计一个图形用户界面(GUI),通过按钮或事件触发线程的创建和同步操作,直观地展示线程间的交互和同步效果。例如,可以模拟银行账户转账,...

    线程 JAVA java线程 java线程第3版 java线程第2版第3版合集

    电子书相关:包含4个有关JAVA线程的电子书(几乎涵盖全部有关线程的书籍) OReilly.Java.Threads.3rd.Edition.Sep.2004.eBook-DDU Java Thread Programming (Sams) java线程第二版中英文 java线程第二版中英文 ...

    Java多线程和同步

    Java线程(二):线程同步synchronized和volatile 详细讲解Java 同步的原理技术资料

    Java多线程同步具体实例.doc

    Java多线程同步是编程中一个非常重要的概念,特别是在并发编程中,用于解决多个线程访问共享资源时可能引发的数据不一致问题。本实例通过一个简单的火车票售票系统来演示同步机制的应用。 在这个实例中,我们创建了...

    JAVA100例之实例65 JAVA线程同步

    4. **ThreadLocal**:每个线程都拥有独立的ThreadLocal变量副本,从而实现了线程间的数据隔离,避免了线程同步问题。 5. **Lock接口**:ReentrantLock是Java提供的一个可重入锁,比synchronized更强大,它可以实现...

    Java线程同步例子.pdf

    在Java中,线程同步是保证多线程安全...上述Java线程同步例子中涉及到的代码虽然是片段,但涵盖了线程同步处理的多个重要方面,帮助我们理解和使用Java线程同步机制,以及在设计和实现多线程应用程序时的实践和技巧。

    java线程线程安全同步线程

    总的来说,理解和掌握Java线程的创建、状态管理、同步机制和线程安全是进行多线程编程的基础,这对于开发高效、稳定的并发程序至关重要。在实际编程中,应充分利用Java提供的工具和机制,避免潜在的并发问题,提升...

    java线程同步基础知识

    Java线程同步是Java编程中一个关键的概念,用于解决多线程环境下的数据一致性问题。在Java中,线程同步主要依赖于监视器(Monitor)机制,它支持两种线程行为:互斥和协作。 互斥是通过对象锁来实现的,确保在任意...

Global site tag (gtag.js) - Google Analytics