package cn.sasa.demo2;

import java.util.concurrent.ExecutionException;

public class ThreadDemo {
public static void main(String[] args) throws InterruptedException, ExecutionException {
//创建Runnable接口实现类对象
Ticket t = new Ticket();
//创建3个Thread类对象,传递Runnable接口实现类
Thread t0 = new Thread(t);
Thread t1 = new Thread(t);
Thread t2 = new Thread(t);
Thread t3 = new Thread(t); t0.start();
t1.start();
t2.start();
t3.start();
/**
* 线程安全问题一般发生在:
* 多线程并发访问同一个数据资源
*
* 通过线程休眠,出现了安全问题
*
* Thread-0 出售第 99
* Thread-1 出售第 98
* Thread-2 出售第 100
* Thread-3 出售第 97
* Thread-1 出售第 96
* Thread-0 出售第 96
* Thread-3 出售第 95
* Thread-2 出售第 94
* Thread-0 出售第 93
* Thread-1 出售第 92
* Thread-3 出售第 91
* Thread-2 出售第 91
* Thread-0 出售第 90
* Thread-1 出售第 90
* Thread-2 出售第 88
* Thread-3 出售第 89
* Thread-0 出售第 87
* Thread-1 出售第 87 ......
*
* 解决安全问题:
* 同步代码块
* synchronized(任意对象){
* 线程要操作的共享数据
* }
* 同步代码块中的锁对象可以是任意对象,
* 但多线程时,要使用同一个锁对象才能够保证线程安全性
*
* 同步方法 在方法声明上加入同步关键字
* eg :
* private synchronized void func(){
* ...
* }
* 同步方法中的对象锁,是本类对象引用 this
* 如果方法是静态的,锁是本类.class属性
*/ }
}
package cn.sasa.demo2;

public class Ticket implements Runnable {
//定义出售的票源
private int ticket = 100;
public static int sum = 100; public void run(){
int flag = 100;
while(flag > 0){
//buyTickets();
buy();
flag --;
}
} //同步方法 synchronized
private synchronized void buyTickets() {
if( ticket > 0){
try {
Thread.sleep(200);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
System.out.println(Thread.currentThread().getName()+" 出售第 "+ticket--);
}
} private static synchronized void buy() {
if( sum > 0){
try {
Thread.sleep(200);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
System.out.println(Thread.currentThread().getName()+" 还剩下。。。 "+sum--);
}
} }

java 线程(四)线程安全 同步方法的更多相关文章

  1. Java多线程(四) 线程池

    一个优秀的软件不会随意的创建.销毁线程,因为创建和销毁线程需要耗费大量的CPU时间以及需要和内存做出大量的交互.因此JDK5提出了使用线程池,让程序员把更多的精力放在业务逻辑上面,弱化对线程的开闭管理 ...

  2. Java多线程(四) —— 线程并发库之Atomic

    一.从原子操作开始 从相对简单的Atomic入手(java.util.concurrent是基于Queue的并发包,而Queue,很多情况下使用到了Atomic操作,因此首先从这里开始). 很多情况下 ...

  3. 重学JAVA基础(四):线程的创建与执行

    1.继承Thread public class TestThread extends Thread{ public void run(){ System.out.println(Thread.curr ...

  4. Java线程:线程的同步-同步方法

    Java线程:线程的同步-同步方法   线程的同步是保证多线程安全访问竞争资源的一种手段. 线程的同步是Java多线程编程的难点,往往开发者搞不清楚什么是竞争资源.什么时候需要考虑同步,怎么同步等等问 ...

  5. JAVA并发实现四(守护线程和线程阻塞)

    守护线程     Java中有两类线程:User Thread(用户线程).Daemon Thread(守护线程) 用户线程即运行在前台的线程,而守护线程是运行在后台的线程. 守护线程作用是为其他前台 ...

  6. 转:【Java并发编程】之四:守护线程与线程阻塞的四种情况

    转载请注明出处:http://blog.csdn.net/ns_code/article/details/17099981      守护线程   Java中有两类线程:User Thread(用户线 ...

  7. java多线程(四)-自定义线程池

    当我们使用 线程池的时候,可以使用 newCachedThreadPool()或者 newFixedThreadPool(int)等方法,其实我们深入到这些方法里面,就可以看到它们的是实现方式是这样的 ...

  8. Java进阶(四十三)线程与进程的区别

    Java进阶(四十三)线程与进程的区别 1.线程的基本概念   概念:线程是进程中执行运算的最小单位,是进程中的一个实体,是被系统独立调度和分派的基本单位,线程自己不拥有系统资源,只拥有一点在运行中必 ...

  9. 【Java并发编程】:守护线程与线程阻塞的四种情况

    守护线程 JAVA中有两类线程:User Thread(用户线程).Daemon Thread(守护线程) 用户线程即运行在前台的线程,而守护线程是运行在后台的线程. 守护线程作用是为其他前台线程的运 ...

  10. 【Java并发编程】之四:守护线程与线程阻塞的四种情况

    守护线程 Java中有两类线程:User Thread(用户线程).Daemon Thread(守护线程) ​ 用户线程即运行在前台的线程,而守护线程是运行在后台的线程. 守护线程作用是为其他前台线程 ...

随机推荐

  1. pyenv BUILD FAILED解决方法

    在本机mac上安装pyenv安装成功后,用pyenv来安装python 3.5.0又出现了如下的问题: -> pyenv install 3.5.0 Downloading Python-3.5 ...

  2. Android Studio下jni应用

    最近在将一个小应用从eclipse开发迁移到android studio,程序中有native代码实现,在eclipse是靠Android.mk这么个mk文件来组织编译的,但到android stud ...

  3. Spark学习笔记——文本处理技术

    1.建立TF-IDF模型 import org.apache.spark.{SparkConf, SparkContext} import org.apache.spark.mllib.linalg. ...

  4. 深入探讨WPF的ListView控件

    接上一篇博客初步探讨WPF的ListView控件(涉及模板.查找子控件)  我们继续探讨ListView的用法      一.实现排序功能 需求是这样的:假如我们把学生的分数放入ListView,当我 ...

  5. iOS开发-- 开发中遇到的问题汇总

    1. CUICatalog: Invalid asset name supplied: 今天写了加载图片,默认图片写的是[UIImage imageNamed:@""],之后就报下 ...

  6. JMeter命令行执行及问题解决 Error in NonGUIDriver java.lang.RuntimeException: Could not find the TestPlan class!

    下面介绍的是在windows环境下如何运行jmeter linux 命令相同      1.首先要准备好脚本,并且设置好线程属性,假设我们设置一个线程,循环一次.                 2. ...

  7. 在一个由 'L' , 'R' 和 'X' 三个字符组成的字符串(例如"RXXLRXRXL")中进行移动操作。一次移动操作指用一个"LX"替换一个"XL",或者用一个"XR"替换一个"RX"。现给定起始字符串start和结束字符串end,请编写代码,当且仅当存在一系列移动操作使得start可以转换成end时, 返回True。

    在一个由 'L' , 'R' 和 'X' 三个字符组成的字符串(例如"RXXLRXRXL")中进行移动操作.一次移动操作指用一个"LX"替换一个"XL ...

  8. 【问题集】redis.clients.jedis.exceptions.JedisDataException: ERR value is not an integer or out of range

    redis.clients.jedis.exceptions.JedisDataException: ERR value is not an integer or out of range incrm ...

  9. 一个表中的id有多个记录,把所有这个id的记录查出来,并显示共有多少条记录数

    一个表中的id有多个记录,把所有这个id的记录查出来,并显示共有多少条记录数 select id ,Count(*) from table_name group by id having count( ...

  10. A - ACM Rank Table

    ACM contests, like the one you are participating in, are hosted by the special software. That softwa ...