一、通过模拟网络延迟,解决同步的问题、

package com.zxf.demo;

public class G01 implements Runnable{

    private int num=10;
private int count=0;
@Override
public void run() {
// TODO Auto-generated method stub
while (true) { count++;
num--;
System.out.println(Thread.currentThread().getName()+"买到了第"+count+"条裤子,还剩"+num+"条裤子"); //模拟网络延迟 让进程睡眠一会 1秒
try {
Thread.sleep(300);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} if (num<=0) {
break;
} } }
public static void main(String[] args) {
G01 g1 = new G01(); Thread t1 = new Thread(g1,"卢本伟");
Thread t2 = new Thread(g1,"马飞飞");
Thread t3 = new Thread(g1,"大司马");
Thread t4 = new Thread(g1,"骚男"); t1.start();
t2.start();
t3.start();
t4.start(); } }

这样写是有问题的  多个进程轮番执行,不能保证每个人买到的东西的唯一性

解决方式?

1.把可能产生的数据安全问题的代码 锁起来, 被锁定的代码就变成单线程的!

package com.zxf.demo;

public class G01 implements Runnable{

    private int num=10;
private int count=0;
@Override
public void run() {
// TODO Auto-generated method stub
while (true) { // 通过synchronized (this){} 将会出问题的部分 锁在这里 ,这里就变了单线程模式 就不会出错!
synchronized (this) {
if (num<=0) {
break;
}
count++;
num--;
System.out.println(Thread.currentThread().getName()+"买到了第"+count+"条裤子,还剩"+num+"条裤子");
} //模拟网络延迟 让进程睡眠一会 1秒
try {
Thread.sleep(300);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} } }
public static void main(String[] args) {
G01 g1 = new G01(); Thread t1 = new Thread(g1,"卢本伟");
Thread t2 = new Thread(g1,"马飞飞");
Thread t3 = new Thread(g1,"大司马");
Thread t4 = new Thread(g1,"骚男"); t1.start();
t2.start();
t3.start();
t4.start(); } }

2.同步方法  就是在方法的返回值类型前边加上 synchronize将该方法内部的代码  全部锁起来

package com.zxf.demo;

public class G01 implements Runnable{

    private int num=10;
private int count=0;
@Override
public void run() {
// TODO Auto-generated method stub
while (true) { if (!buy()) { // 调用buy的方法 不满足结果 结束循环
break;
} //模拟网络延迟 让进程睡眠一会 1秒
try {
Thread.sleep(300);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} } }
//同步方法 定义一个方法 需要在方法的返回值类型 前边加上 synchronized 关键字。
public synchronized boolean buy() { if (num<=0) {
return false;
}
num--;
count++;
System.out.println(Thread.currentThread().getName()+"买到了第"+count+"条裤子,还剩"+num+"条裤子"); return true; } public static void main(String[] args) {
G01 g1 = new G01(); Thread t1 = new Thread(g1,"卢本伟");
Thread t2 = new Thread(g1,"马飞飞");
Thread t3 = new Thread(g1,"大司马");
Thread t4 = new Thread(g1,"骚男"); t1.start();
t2.start();
t3.start();
t4.start(); } }

java多线程中同步的问题?的更多相关文章

  1. java多线程中并发集合和同步集合有哪些?区别是什么?

    java多线程中并发集合和同步集合有哪些? hashmap 是非同步的,故在多线程中是线程不安全的,不过也可以使用 同步类来进行包装: 包装类Collections.synchronizedMap() ...

  2. Java多线程中的竞争条件、锁以及同步的概念

    竞争条件 1.竞争条件: 在java多线程中,当两个或以上的线程对同一个数据进行操作的时候,可能会产生“竞争条件”的现象.这种现象产生的根本原因是因为多个线程在对同一个数据进行操作,此时对该数据的操作 ...

  3. Java多线程中易混淆的概念

    概述 最近在看<ThinKing In Java>,看到多线程章节时觉得有一些概念比较容易混淆有必要总结一下,虽然都不是新的东西,不过还是蛮重要,很基本的,在开发或阅读源码中经常会遇到,在 ...

  4. java多线程中的三种特性

    java多线程中的三种特性 原子性(Atomicity) 原子性是指在一个操作中就是cpu不可以在中途暂停然后再调度,既不被中断操作,要不执行完成,要不就不执行. 如果一个操作时原子性的,那么多线程并 ...

  5. java多线程中最佳的实践方案是什么?

    java多线程中最佳的实践方案是什么? 给你的线程起个有意义的名字.这样可以方便找bug或追踪.OrderProcessor, QuoteProcessor or TradeProcessor 这种名 ...

  6. Java多线程的同步控制记录

    Java多线程的同步控制记录 一.重入锁 重入锁完全可以代替 synchronized 关键字.在JDK 1.5 早期版本,重入锁的性能优于 synchronized.JDK 1.6 开始,对于 sy ...

  7. Java多线程中的常用方法

    本文将带你讲诉Java多线程中的常用方法   Java多线程中的常用方法有如下几个 start,run,sleep,wait,notify,notifyAll,join,isAlive,current ...

  8. Java多线程之同步集合和并发集合

    Java多线程之同步集合和并发集合 不管是同步集合还是并发集合他们都支持线程安全,他们之间主要的区别体现在性能和可扩展性,还有他们如何实现的线程安全. 同步集合类 Hashtable Vector 同 ...

  9. Java多线程编程(同步、死锁、生产消费者问题)

    Java多线程编程(同步.死锁.生产消费): 关于线程同步以及死锁问题: 线程同步概念:是指若干个线程对象并行进行资源的访问时实现的资源处理保护操作: 线程死锁概念:是指两个线程都在等待对方先完成,造 ...

随机推荐

  1. 【LeetCode】462. Minimum Moves to Equal Array Elements II 解题报告(Python & C++)

    作者: 负雪明烛 id: fuxuemingzhu 个人博客: http://fuxuemingzhu.cn/ 目录 题目描述 题目大意 解题方法 方法一:排序 方法二:直接找中位数 日期 题目地址: ...

  2. toString()、String.valueOf、(String)强转

    1.基本类型 (1)基本类型没有toString()方法 (2)推荐使用String.valueOf(); (3)无法强转 =========补========= (String)是标准的类型转换,将 ...

  3. delete、truncate、drop

    DELETE DELETE属于数据库DML操作语言,只删除数据不删除表的结构,会走事务,执行时会触发trigger:每次从表中删除一行,并且同时将该行的的删除操作记录在redo和undo表空间中以便进 ...

  4. Chapter 10 Random Variability

    目录 10.1 Identification versus estimation 10.2 Estimation of causal effects 10.3 The myth of the supe ...

  5. Distillation as a Defense to Adversarial Perturbations against Deep Neural Networks

    目录 概 主要内容 算法 一些有趣的指标 鲁棒性定义 合格的抗干扰机制 Nicolas Papernot, Patrick McDaniel, Xi Wu, Somesh Jha, Ananthram ...

  6. 更新系统为High sierra 后无法使用Cocoapods

    sudo gem update --system sudo gem install -n /usr/local/bin cocoapods执行完就可以直接用了.

  7. Java面向对象笔记 • 【第3章 继承与多态】

    全部章节   >>>> 本章目录 3.1 包 3.1.1 自定义包 3.1.2 包的导入 3.1.3 包的访问权限 3.1.4 实践练习 3.2 继承 3.2.1 继承概述 3 ...

  8. Go 通过 Map/Filter/ForEach 等流式 API 高效处理数据

    什么是流处理 如果有 java 使用经验的同学一定会对 java8 的 Stream 赞不绝口,极大的提高了们对于集合类型数据的处理能力. int sum = widgets.stream() .fi ...

  9. 『无为则无心』Python函数 — 33、高阶函数

    目录 1.高阶函数的定义 2.体验高阶函数 3.内置高阶函数 (1)map()函数 (2)reduce()函数 (3)filter()函数 1.高阶函数的定义 把函数作为参数传入(把一个函数作为另外一 ...

  10. python + requests发起请求,接口返回400,报错“Unexpected character encountered while parsing value: G. Path”

    完整报错信息如下: {'errors': {'': ["Unexpected character encountered while parsing value: G. Path '', l ...