Java多线程-线程的同步(同步代码块)

转载 2013年12月02日 13:46:28
对于同步,除了同步方法外,还可以使用同步代码块,有时候同步代码块会带来比同步方法更好的效果。

追其同步的根本的目的,是控制竞争资源的正确的访问,因此只要在访问竞争资源的时候保证同一时刻只能一个线程访问即可,因此Java引入了同步代码快的策略,以提高性能。

在上个例子的基础上,对oper方法做了改动,由同步方法改为同步代码块模式,程序的执行逻辑并没有问题。

package thread;

/**
 * 线程同步方法
 * 
 * @author administrator
 * 
 */
public class ThreadSynchronizedCode {

	public static void main(String[] args) {
		ThreadSynchronizedCode t = new ThreadSynchronizedCode();
		User u = t.new User("张三", 100);
		MyThread t1 = t.new MyThread("线程A", u, 20);
		MyThread t2 = t.new MyThread("线程B", u, -60);
		MyThread t3 = t.new MyThread("线程C", u, -80);
		MyThread t4 = t.new MyThread("线程D", u, -30);
		MyThread t5 = t.new MyThread("线程E", u, 32);
		MyThread t6 = t.new MyThread("线程F", u, 21);

		t1.start();
		t2.start();
		t3.start();
		t4.start();
		t5.start();
		t6.start();
	}

	class MyThread extends Thread {
		private User u;
		/** 存款金额 */
		private int y = 0;

		MyThread(String name, User u, int y) {
			super(name);
			this.u = u;
			this.y = y;
		}

		public void run() {
			u.oper(y);
		}
	}

	class User {
		/** 账号 */
		private String code;
		/** 余额 */
		private int cash;

		User(String code, int cash) {
			this.code = code;
			this.cash = cash;
		}

		public String getCode() {
			return code;
		}

		public void setCode(String code) {
			this.code = code;
		}

		/**
		 * 存款
		 * 
		 * @param x
		 *            欲存款金额
		 * 
		 */
		public void oper(int x) {
			try {
				Thread.sleep(10L);
				synchronized (this) {
					this.cash += x;
					System.out.println("线程" + Thread.currentThread().getName()
							+ "运行结束,增加“" + x + "”,当前用户账户余额为:" + cash);
				}
				Thread.sleep(10L);
			} catch (InterruptedException e) {
				e.printStackTrace();
			}
		}

		@Override
		public String toString() {
			return "User{" + "code='" + code + '\'' + ", cash=" + cash + '}';
		}
	}
}

运行结果:

线程线程A运行结束,增加“20”,当前用户账户余额为:120
线程线程B运行结束,增加“-60”,当前用户账户余额为:60
线程线程C运行结束,增加“-80”,当前用户账户余额为:-20
线程线程E运行结束,增加“32”,当前用户账户余额为:12
线程线程D运行结束,增加“-30”,当前用户账户余额为:-18
线程线程F运行结束,增加“21”,当前用户账户余额为:3


(二) Java多线程详解之同步代码块synchronized和线程通信详解

在同一程序中运行多个线程本身不会导致问题,问题在于多个线程访问了相同的资源,并且对资源做了写操作时,可能会导致数据混乱。这里用了卖票的例子,代码如下:public class ThreadExampl...
  • RobertoHuang
  • RobertoHuang
  • 2017年05月17日 22:06
  • 812

多线程14__Java同步代码块,同步方法

同步代码块 参见http://www.cnblogs.com/sunzn/archive/2013/02/13/2910895.html,这里改为限制循环次数50次: new Thread() ...
  • aduovip
  • aduovip
  • 2015年04月25日 13:17
  • 1370

java同步方法和同步代码块

java synchronized详解 记下来,很重要。 Java语言的关键字,当它用来修饰一个方法或者一个代码块的时候,能够保证在同一时刻最多只有一个线程执行该段代码。      一、当两个并...
  • zhenwodefengcaii
  • zhenwodefengcaii
  • 2017年01月18日 14:45
  • 5550

JAVA之旅(十三)——线程的安全性,synchronized关键字,多线程同步代码块,同步函数,同步函数的锁是this

JAVA之旅(十三)——线程的安全性, 我们继续上个篇幅接着讲线程的知识点 一.线程的安全性 当我们开启四个窗口(线程)把票陆陆续续的卖完了之后,我们要反思一下,这里面有没有安全隐患呢?在实际...
  • qq_26787115
  • qq_26787115
  • 2016年06月04日 18:34
  • 9171

java 多线程学习笔记2-同步代码块,死锁

1、多线程-同步代码块:synchronized     当多线程并发, 有多段代码同时执行时, 我们希望某一段代码执行的过程中CPU不要切换到其他线程工作. 这时就需要同步。     如...
  • gaopinqiang
  • gaopinqiang
  • 2016年12月18日 15:08
  • 651

线程中的同步代码块synchronized、同步方法和同步锁Lock

在学习线程的时候,因为线程的调度具有不确定性,所以银行取钱问题、多个窗口售卖火车票问题都是反应多线程的优越性以及不确定性。当程序中有多个并发线程在进入一个代码块中并且修改其中参数时,就很有可能引发线程...
  • sinat_15274667
  • sinat_15274667
  • 2015年11月01日 17:35
  • 3472

线程安全问题之线程同步机制(同步代码块)

继续讨论多窗口卖票问题中的线程安全问题: 方式二: 一、问题: 出现了线程安全问题 ? 二、问题的原因: 当多条语句在操作同一个线程共享数据时,一个线程对多条语句只执行了一部分,还没有执行完,另...
  • qq_34944851
  • qq_34944851
  • 2016年08月06日 22:55
  • 338

JAVA 同步代码块synchronized

//仅作为学习笔记 /* JAVA对于多线程的安全问题提供了专业的解决方式 就是同步代码块 synchronized(对象)//这个对象可以为任意对象 { 需要被同步的代码 } 对象如同锁...
  • wu_lai_314
  • wu_lai_314
  • 2013年03月10日 14:49
  • 27351

线程安全问题(银行取钱问题)、同步代码块、同步方法

(1)线程安全问题: 关于线程安全问题,有一个经典的问题–银行取钱问题。银行取钱可以分为以下步骤: 1.用户输入账户密码,系统判断账户密码是否匹配 2.用户输入取款金额 3.系统判断账户余额是...
  • zlz18225318697
  • zlz18225318697
  • 2016年09月21日 13:56
  • 853

Java之同步代码块实现取钱实例

package 线程同步; public class Account { // 封装账号编号、账号余额的两个成员变量 private String accountNo; private dou...
  • qq_31028891
  • qq_31028891
  • 2016年10月28日 00:04
  • 766
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:Java多线程-线程的同步(同步代码块)
举报原因:
原因补充:

(最多只允许输入30个字)