java中synchronized的关键字

java中每个对象都会有一个对象锁,而synchronized就是得到这个锁,看下面这个例子

import java.util.Random;
public class MyData{

    public synchronized void increment() {
        for (int i = 0; i < 10; i++) {
            try {
                Thread.sleep(new Random().nextInt(200));
            } catch (Exception e) {
                e.printStackTrace();
            }
           System.out.println(Thread.currentThread().getName() + ":" +i);
        }
    }

    public synchronized void decrement() {
        for (int i = 0; i < 10; i++) {
            try {
                Thread.sleep(new Random().nextInt(200));
            } catch (Exception e) {
                e.printStackTrace();
            }
            System.out.println(Thread.currentThread().getName() + ":" +i);
        }
    }

    public static void main(String[] args) {
        final MyData myData1 = new MyData();
       // final MyData myData2 = new MyData();
       new Thread(new Runnable() {
            @Override
            public void run() {
                myData1.increment();
            }
        }).start();

        new Thread(new Runnable() {
            @Override
            public void run() {
                myData1.decrement();
            }
        }).start();
    }
}

无论执行多少次都是有序的,两个线程操作的是同一个对象,第一个执行的线程得到了锁,第二个线程只能等第一个线程执行完了才能拿到锁,进入方法。

再看下面这个例子

import java.util.Random;
public class MyData{

    public synchronized void increment() {
        for (int i = 0; i < 10; i++) {
            try {
                Thread.sleep(new Random().nextInt(200));
            } catch (Exception e) {
                e.printStackTrace();
            }
           System.out.println(Thread.currentThread().getName() + ":" +i);
        }
    }

    public synchronized void decrement() {
        for (int i = 0; i < 10; i++) {
            try {
                Thread.sleep(new Random().nextInt(200));
            } catch (Exception e) {
                e.printStackTrace();
            }
            System.out.println(Thread.currentThread().getName() + ":" +i);
        }
    }

    public static void main(String[] args) {
        final MyData myData1 = new MyData();
        final MyData myData2 = new MyData();
       new Thread(new Runnable() {
            @Override
            public void run() {
                myData1.increment();
            }
        }).start();

        new Thread(new Runnable() {
            @Override
            public void run() {
                myData2.decrement();
            }
        }).start();
    }
}

执行的结果是无序的,两个对象,两把锁,故互不影响,各自执行各自的。

再来看看下面这个例子

import java.util.Random;public class MyData{        public synchronized void increment() {        for (int i = 0; i < 10; i++) {            try {                Thread.sleep(new Random().nextInt(200));            } catch (Exception e) {                e.printStackTrace();            }           System.out.println(Thread.currentThread().getName() + ":" +i);        }    }        public static synchronized void decrement() {        for (int i = 0; i < 10; i++) {            try {                Thread.sleep(new Random().nextInt(200));            } catch (Exception e) {                e.printStackTrace();            }            System.out.println(Thread.currentThread().getName() + ":" +i);        }    }        public static void main(String[] args) {        final MyData myData1 = new MyData();      //  final MyData myData2 = new MyData();       new Thread(new Runnable() {            @Override            public void run() {                myData1.increment();            }        }).start();                new Thread(new Runnable() {            @Override            public void run() {                MyData.decrement();            }        }).start();    }}

结果也是无序的,原因和上面一样,static方法是属于Class对象的,故decrement方法锁的MyData.Class对象,而myData1.increment();锁的是myData1对象,互不干扰。

只需记住synchronized锁的是对象,每个对象有一把对象锁,拿到锁之后才能执行synchronized的方法

时间: 2024-10-20 23:10:29

java中synchronized的关键字的相关文章

理解java中的volatile关键字

Java语言包含两种内在的同步机制:同步块(或方法)和 volatile 变量.这两种机制的提出都是为了 实现代码线程的安全性.Java 语言中的 volatile 变量可以被看作是一种 "程度较轻的 synchronized":与 synchronized 块相比,volatile 变量所需的编码较少,并且运行时开销也较少,但是它所能实现的功能也仅是 synchronized 的一部分. volatile 写和读的内存语义: 线程 A 写一个 volatile 变量,实质上是线程 A

java中 synchronized 的使用,确保异步执行某一段代码。

最近看了个有关访问网络url和下载的例子,里面有几个synchronized的地方,系统学习下,以下内容很重要,记下来. Java语言的关键字,当它用来修饰一个方法或者一个代码块的时候,能够保证在同一时刻最多只有一个线程执行该段代码. 一.当两个并发线程访问同一个对象object中的这个synchronized(this)同步代码块时,一个时间内只能有一个线程得到执行.另一个线程必须等待当前线程执行完这个代码块以后才能执行该代码块. 二.然而,当一个线程访问object的一个synchroniz

java中synchronized的用法与详解

Java语言的关键字,当它用来修饰一个方法或者一个代码块的时候,能够保证在同一时刻最多只有一个线程执行该段代码. 一.当两个并发线程访问同一个对象object中的这个synchronized(this)同步代码块时,一个时间内只能有一个线程得到执行.另一个线程必须等待当前线程执行完这个代码块以后才能执行该代码块. 二.然而,当一个线程访问object的一个synchronized(this)同步代码块时,另一个线程仍然可以访问该object中的非synchronized(this)同步代码块.

java中synchronized与lock的理解与应用

总结来说,Lock和synchronized有以下几点不同: 1)Lock是一个接口,而synchronized是Java中的关键字,synchronized是内置的语言实现: 2)synchronized在发生异常时,会自动释放线程占有的锁,因此不会导致死锁现象发生:而Lock在发生异常时,如果没有主动通过unLock()去释放锁,则很可能造成死锁现象,因此使用Lock时需要在finally块中释放锁: 3)Lock可以让等待锁的线程响应中断,而synchronized却不行,使用synchr

浅析Java中的final关键字

原文出处: 海子 谈到final关键字,想必很多人都不陌生,在使用匿名内部类的时候可能会经常用到final关键字.另外,Java中的String类就是一个final类,那么今天我们就来了解final这个关键字的用法.下面是本文的目录大纲: 一.final关键字的基本用法 二.深入理解final关键字 若有不正之处,请多多谅解并欢迎指正. 一.final关键字的基本用法 在Java中,final关键字可以用来修饰类.方法和变量(包括成员变量和局部变量).下面就从这三个方面来了解一下final关键字

转载:浅析Java中的final关键字

文章转自:http://www.cnblogs.com/dolphin0520/p/3736238.html 谈到final关键字,想必很多人都不陌生,在使用匿名内部类的时候可能会经常用到final关键字.另外,Java中的String类就是一个final类,那么今天我们就来了解final这个关键字的用法.下面是本文的目录大纲: 一.final关键字的基本用法 二.深入理解final关键字 若有不正之处,请多多谅解并欢迎指正. 请尊重作者劳动成果,转载请标明原文链接: http://www.cn

(转)Java中的static关键字解析

转载: http://www.cnblogs.com/dolphin0520/p/3799052.html 一.static关键字的用途 在<Java编程思想>P86页有这样一段话: "static方法就是没有this的方法.在static方法内部不能调用非静态方法,反过来是可以的.而且可以在没有创建任何对象的前提下,仅仅通过类本身来调用static方法.这实际上正是static方法的主要用途." 这段话虽然只是说明了static方法的特殊之处,但是可以看出static关键

Java中的static关键字解析

http://www.cnblogs.com/dolphin0520/p/3799052.html 一.static关键字的用途 在<Java编程思想>P86页有这样一段话: “static方法就是没有this的方法.在static方法内部不能调用非静态方法,反过来是可以的.而且可以在没有创建任何对象的前提下,仅仅通过类本身来调用static方法.这实际上正是static方法的主要用途.” 这段话虽然只是说明了static方法的特殊之处,但是可以看出static关键字的基本作用,简而言之,一句

Java中的null关键字

先看一段代码 public class NULL { public static void Test(){ System.out.println("这是Test()的输出!!"); } public static void main(String[] args) { ((NULL)null).Test(); } } 上面的代码有没有错误? 答案是没有!! 编译运行 输出结果: 这是Test()的输出!! 这是因为Java中,null是一个关键字,用来标识一个不确定的对象.因此可以将nu