java基础温习 -- Thread synchronized关键字
synchronized 基本规则
1. 当一个线程访问“某对象”的“synchronized方法”或者“synchronized代码块”时,其他线程对“该对象”的该“synchronized方法”或者“synchronized代码块”的访问将被阻塞。
class MyRunable implements Runnable {
public void run() {
synchronized (this) { // this是指“当前的类对象” 此处为MyRunable对象 demo
try {
for (int i = 0; i < 5; i++) {
Thread.sleep(100); // 休眠100ms
System.out.println(Thread.currentThread().getName() + " loop " + i);
}
} catch (InterruptedException ie) {
}
}
}
}
public class Demo1_1 {
public static void main(String[] args) {
Runnable demo = new MyRunable(); // 新建“Runnable对象”
Thread t1 = new Thread(demo, "t1"); // 新建“线程t1”, t1是基于demo这个Runnable对象
Thread t2 = new Thread(demo, "t2"); // 新建“线程t2”, t2是基于demo这个Runnable对象
t1.start(); // 启动“线程t1”
t2.start(); // 启动“线程t2”
}
}
===========
t1 loop 0
t1 loop 1
t1 loop 2
t1 loop 3
t1 loop 4
t2 loop 0
t2 loop 1
t2 loop 2
t2 loop 3
t2 loop 4
2. 当一个线程访问“某对象”的“synchronized方法”或者“synchronized代码块”时,其他线程仍然可以访问“该对象”的非同步代码块。
3. 当一个线程访问“某对象”的“synchronized方法”或者“synchronized代码块”时,其他线程对“该对象”的其他的“synchronized方法”或者“synchronized代码块”的访问将被阻塞。
这种机制确保了同一时刻对于每一个类实例,其所有声明为 synchronized 的成员函数中至多只有一个处于可执行状态(因为至多只有一个能够获得该类实例对应的锁),从而有效避免了类成员变量的访问冲突(只要所有可能访问类成员变量的方法均被声明为 synchronized)。
synchronized 方法 和 synchronized 代码块
(假设P1、P2是同一个类的不同对象,类中定义了同步块或同步方法,P1 P2都可以调用它。)
Public synchronized void methodA()
{
//….
}
等同于
public void methodA()
{
synchronized (this) // this指的就是调用这个方法的对象,如P1
{
//…..
}
}
同步块:
public void method3(SomeObject so)
{
synchronized(so) // 锁是so这个对象(当有一个明确的对象作为锁时,可以这样写)
{
//…..
}
}
当有一个明确的对象作为锁时,就可以这样写程序,但当没有明确的对象作为锁,只是想让一段代码同步时,可以创建一个特殊的instance变量(它得是一个对象)来充当锁:
class Foo implements Runnable
{
private byte[] lock = new byte[0]; // 零长度的byte数组充当锁
Public void methodA()
{
synchronized(lock) {
//…
}
}
//…..
}
synchronized 修饰static方法
Class Foo
{
public synchronized static void methodA() // 同步的static方法
{
//….
} public void methodB()
{
synchronized(Foo.class) // 锁当前调用这个方法的对象所属的类
}
}
methodB()方法是把class literal作为锁的情况,它和同步的static函数产生的效果是一样的,取得的锁很特别,是当前调用这
个方法的对象所属的类(Class,而不再是由这个Class产生的某个具体对象了)
实例锁 和 全局锁
实例锁 -- 锁在某一个实例对象上。如果该类是单例,那么该锁也具有全局锁的概念。 实例锁对应的就是synchronized关键字。
全局锁 -- 该锁针对的是类,无论实例多少个对象,那么线程都共享该锁。 全局锁对应的就是static synchronized(或者是锁在该类的class或者classloader对象上)。
// 举例
pulbic class Something {
public synchronized void isSyncA(){}
public synchronized void isSyncB(){}
public static synchronized void cSyncA(){}
public static synchronized void cSyncB(){}
} 假设,Something有两个实例x和y。分析下面4组表达式获取的锁的情况。
(1) x.isSyncA()与x.isSyncB() // 不能同时访问,都是锁的对象x
(2) x.isSyncA()与y.isSyncA() // 可以同时访问,锁的不是同一个对象
(3) x.cSyncA()与y.cSyncB() // 不能同时访问,static方法,两个都相当于Something.isSyncA()。锁的同一个类
(4) x.isSyncA()与Something.cSyncA() // 可以同时访问,x.isSyncA()使用的是对象x的锁;而cSyncA()是静态方法,Something.cSyncA()可以理解对使用的是“类的锁”。
java基础温习 -- Thread synchronized关键字的更多相关文章
- java基础温习 -- Thread
启动线程两种方式: 1. 实现Runnable接口: 2. 继承Thread类. 选用:能使用接口,就不用从Thread类继承. 使用继承的方法不够灵活,从这个类继承了就不能从其他类继承: 实现 ...
- JAVA多线程之Synchronized关键字--对象锁的特点
一,介绍 本文介绍JAVA多线程中的synchronized关键字作为对象锁的一些知识点. 所谓对象锁,就是就是synchronized 给某个对象 加锁.关于 对象锁 可参考:这篇文章 二,分析 s ...
- Java并发编程(一):线程基础知识以及synchronized关键字
1.线程与多线程的概念:在一个程序中,能够独立运行的程序片段叫作“线程”(Thread).多线程(multithreading)是指从软件或者硬件上实现多个线程并发执行的技术. 2.多线程的意义:多线 ...
- Java多线程4:synchronized关键字
原文:http://www.cnblogs.com/skywang12345/p/3479202.html 1. synchronized原理在java中,每一个对象有且仅有一个同步锁.这也意味着,同 ...
- 搜狗一道java题目 关于对象 synchronized 关键字作用在 int, integer
第一次见到这个题目,我觉得自己没学到java,太浅了,其实这个问题没有考synchronized关键字,只是考什么是对象? 1.在java编程思想的第二章有一句话; 一切都是对象,很可惜int,c ...
- java线程学习之synchronized关键字
关键字synchronized的作用是实现线程间的同步.它的任务是对同步的代码加锁.一个代码块同时只能有同一个线程进行读和写操作,从而保证线程间是安全的. 线程安全的概念是:当多个线程访问某一个类(对 ...
- Java 基础(6)——关键字 & 标识符 & 转义字符
依然是基础的一天,看一看就好~ 关键字 之前就有说过关键字哦~ 注:关键字就是程序发明者规定的有特殊含义的单词. from Java基础(2) Java 中除了关键字以外还有暂时没有成为关键字的保留字 ...
- 2.3多线程(java学习笔记)synchronized关键字
一.为什么要用synchronized关键字 首先多线程中多个线程运行面临共享数据同步的问题. 多线程正常使用共享数据时需要经过以下步骤: 1.线程A从共享数据区中复制出数据副本,然后处理. 2.线程 ...
- 【Java并发编程】Synchronized关键字实现原理
想必在面试中经常会被问到Synchronized关键字,它有什么特性,原理什么 它的主要特性是同步锁.非公平锁.阻塞锁.可以保证线程安全(可见性.原子性.有序性) JDK1.6之后对Synchroni ...
随机推荐
- SVN Cannot merge into a working copy that has local modifications
我尝试了 主支,分支都提交,但是依然无法合并. 最终,我在服务器上将分支删除,然后主支在拷贝过去. 一,打开服务器资源 二,删除分支 三,拷贝主支到分支 四,刷新分支,就能看到了. 然后在分支项目中, ...
- UOJ67 新年的毒瘤【Tarjan,割点】
Online Judge:#uoj 67 Label:Tarjan,割点,细节 题目描述 辞旧迎新之际,喜羊羊正在打理羊村的绿化带,然后他发现了一棵长着毒瘤的树.这个长着毒瘤的树可以用\(n\)个结点 ...
- 01.SpringMVC快速入门
1.导入jar包 2.在web.xml中配置前端控制器 <!-- spring前端控制器 --> <servlet> <servlet-name>springmvc ...
- excel 导数据
参考: ="insert tsilverinfo(ss_id,memo,ss_weight,ts_id,ss_type,ModelPosX,ss_stoneW,ss_stoneWU) val ...
- Binary XML file line #23: Error inflating class android.widget.TextView
分析一波,报错23行TextView的问题,但是检查了xml没有发现23行又TextView相关代码,就不应该继续纠结xml了,代码是通过R文件拿到xml资源的,你就应该怀疑是R文件的问题,R文件编译 ...
- JS的十大经典算法
冒泡排序(Bubble Sort) 冒泡排序须知: 作为最简单的排序算法之一,冒泡排序给我的感觉就像Abandon在单词书里出现的感觉一样,每次都在第一页第一位,所以最熟悉...冒泡排序还有一种优化算 ...
- memset 初始化 不同数值 打表
#include <cstdio> #include <cstdlib> #include <cmath> #include <cstring> #in ...
- BigDecimal踩过的大坑
通常Java中涉及金钱相关的计算为了保持精度,会采用BigDecimal来实现,但是BigDecimal中创建BigDecimal类对象的时候,如果使用直接new的话,必须是String类型的参数,否 ...
- mysql 主从笔记
主库配置 一.修改主库配置文件 开启binlog,并设置server-id,每次修改配置文件后都要重启mysql服务才会生效 server-id = log-bin = mysql-bin binlo ...
- js字符串去重复
var str="fdafdasfdasfdsfdseeeu"; function te(str){ var hash=[]; var arr=new Array(); var s ...