java 并发synchronized使用

从版本1.0开始,java中每个对象都有一个内部锁,如果一个方法用synchronized修饰,那么对象的锁将保护整个方法,也就是说要调用该方法,线程必须获得内部的对象锁

换句话说

public synchronized void method(){

  method body

}

等价于

public void method(){

this.lock();
try{
method body;
}
finally{this.unlock}

}

内部对象只有一个相关条件,wait方法添加一个线程到等待集中,notifyAll方法解除等待线程的阻塞状态

package reentrant_lock;

/**
 * Created by luozhitao on 2017/8/23.
 */
public class bank_syn {

    private double [] accounts;

    public bank_syn(int n,double bance){

        accounts=new double[n];

        for(int i=0;i<n;i++){

            accounts[i]=bance;

        }

    }
//

    public synchronized  void tansfer(int from,int to,double transf_num) throws InterruptedException{

        while (accounts[from]<transf_num)
            wait();

        accounts[from]-=transf_num;
        System.out.printf("转出账户转出%f 剩余 %10.2f",transf_num,accounts[from]);

        accounts[to]+=transf_num;
        System.out.printf("转入账户目前余额为 %10.2f",accounts[to]);

        notifyAll();
        System.out.printf(" 目前所有账户总额为 %10.2f",get_total());

    }

    public synchronized double get_total(){

        double sum=0;

        for (double d:accounts){

            sum+=d;
        }

        return sum;
    }

    //
    public int size(){

        return accounts.length;
    }

}

主线程

package reentrant_lock;

/**
 * Created by luozhitao on 2017/8/18.
 */
public class transferRunnable implements Runnable {

 //   private Bank bank;
    private bank_syn bank;
    private int fromAccount;
    private double maxAccount;
    private int DELAY=10;
    int flag=0;

    public transferRunnable(bank_syn b,int from,double max){
        this.bank=b;
        this.fromAccount=from;
        this.maxAccount=max;

    }

    public void run() {

        try{
            while (true){
                int toAccount=(int)((bank.size()-1)*Math.random());

                System.out.println("toAccount ="+toAccount);
                double account_m=maxAccount*Math.random();
                System.out.println("account_m is "+account_m);
                bank.tansfer(fromAccount,toAccount,account_m);

                Thread.sleep((int) (DELAY * Math.random()));
                flag++;

            }
        }catch (InterruptedException e){e.printStackTrace();}

    }
}

main

package reentrant_lock;

/**
 * Created by luozhitao on 2017/8/23.
 */
public class bank_testsyn {

    private static int accoun_num=100;
    private static double init_num=1000;

    public static void main(String [] args){

        bank_syn syn=new bank_syn(accoun_num,init_num);

        for(int i=0;i<accoun_num;i++){
            transferRunnable transferrun = new transferRunnable(syn,i,init_num);
            Thread t=new Thread(transferrun);
            t.start();

        }

    }

}
时间: 2024-08-06 03:47:09

java 并发synchronized使用的相关文章

Java 并发:内置锁 Synchronized

摘要: 在多线程编程中,线程安全问题是一个最为关键的问题,其核心概念就在于正确性,即当多个线程访问某一共享.可变数据时,始终都不会导致数据破坏以及其他不该出现的结果.而所有的并发模式在解决这个问题时,采用的方案都是序列化访问临界资源 .在 Java 中,提供了两种方式来实现同步互斥访问:synchronized 和 Lock.本文针对 synchronized 内置锁 详细讨论了其在 Java 并发 中的应用,包括它的具体使用场景(同步方法.同步代码块.实例对象锁 和 Class 对象锁).可重

【Java并发系列04】线程锁synchronized和Lock和volatile和Condition

img { border: solid 1px } 一.前言 多线程怎么防止竞争资源,即防止对同一资源进行并发操作,那就是使用加锁机制.这是Java并发编程中必须要理解的一个知识点.其实使用起来还是比较简单,但是一定要理解. 有几个概念一定要牢记: 加锁必须要有锁 执行完后必须要释放锁 同一时间.同一个锁,只能有一个线程执行 二.synchronized synchronized的特点是自动释放锁,作用在方法时自动获取锁,任意对象都可做为锁,它是最常用的加锁机制,锁定几行代码,如下: //---

Java并发编程 Synchronized及其实现原理

Synchronized是Java中解决并发问题的一种最常用的方法,也是最简单的一种方法.Synchronized的作用主要有三个:(1)确保线程互斥的访问同步代码(2)保证共享变量的修改能够及时可见(3)有效解决重排序问题. Java中每一个对象都可以作为锁,这是synchronized实现同步的基础: 1.普通同步方法,锁是当前实例对象 public class SynchronizedTest { 4 public synchronized void method1(){ 5 System

Java并发编程:Synchronized底层优化(偏向锁、轻量级锁)

Java并发编程系列[未完]: Java 并发编程:核心理论 Java并发编程:Synchronized及其实现原理 Java并发编程:Synchronized底层优化(轻量级锁.偏向锁) 一.重量级锁 上篇文章中向大家介绍了Synchronized的用法及其实现的原理.现在我们应该知道,Synchronized是通过对象内部的一个叫做监视器锁(monitor)来实现的.但是监视器锁本质又是依赖于底层的操作系统的Mutex Lock来实现的.而操作系统实现线程之间的切换这就需要从用户态转换到核心

Java并发编程:Synchronized及其实现原理

Java并发编程系列[未完]: Java 并发编程:核心理论 Java并发编程:Synchronized及其实现原理 一.Synchronized的基本使用 Synchronized是Java中解决并发问题的一种最常用的方法,也是最简单的一种方法.Synchronized的作用主要有三个:(1)确保线程互斥的访问同步代码(2)保证共享变量的修改能够及时可见(3)有效解决重排序问题.从语法上讲,Synchronized总共有三种用法: (1)修饰普通方法 (2)修饰静态方法 (3)修饰代码块 接下

JAVA并发编程3_线程同步之synchronized关键字

在上一篇博客里讲解了JAVA的线程的内存模型,见:JAVA并发编程2_线程安全&内存模型,接着上一篇提到的问题解决多线程共享资源的情况下的线程安全问题. 不安全线程分析 public class Test implements Runnable { private int i = 0; private int getNext() { return i++; } @Override public void run() { // synchronized while (true) { synchro

【转】Java并发编程:Synchronized及其实现原理

一.Synchronized的基本使用 Synchronized是Java中解决并发问题的一种最常用的方法,也是最简单的一种方法.Synchronized的作用主要有三个:(1)确保线程互斥的访问同步代码(2)保证共享变量的修改能够及时可见(3)有效解决重排序问题.从语法上讲,Synchronized总共有三种用法: (1)修饰普通方法 (2)修饰静态方法 (3)修饰代码块 接下来我就通过几个例子程序来说明一下这三种使用方式(为了便于比较,三段代码除了Synchronized的使用方式不同以外,

Java并发编程

synchronized是Java中的关键字,在并发编程中被称为内置锁或者监视器锁.当用它来修饰一个方法或者一个代码块的时候能够保证同一时刻最多只有一个线程执行该段代码. Java的内置锁相当于一种互斥锁,最多只有一个线程能够持有这种锁,故而由这个锁保护的同步代码块会以原子方式执行,多个线程在执行该代码时就不会相互干扰. 但由于被锁保护的同步块代码是以串行形式来访问的,即多个线程以独占的方式访问对象,而这也导致如果被锁保护的同步代码块的作用范围过大,会导致并发不良. 这里有必要简单讲一下内置锁的

【死磕Java并发】-----J.U.C之重入锁:ReentrantLock

此篇博客所有源码均来自JDK 1.8 ReentrantLock,可重入锁,是一种递归无阻塞的同步机制.它可以等同于synchronized的使用,但是ReentrantLock提供了比synchronized更强大.灵活的锁机制,可以减少死锁发生的概率. API介绍如下: 一个可重入的互斥锁定 Lock,它具有与使用 synchronized 方法和语句所访问的隐式监视器锁定相同的一些基本行为和语义,但功能更强大.ReentrantLock 将由最近成功获得锁定,并且还没有释放该锁定的线程所拥