java——多线程的实现方式、三种办法解决线程赛跑、多线程数据同步(synchronized)、死锁
多线程的实现方式:demo1、demo2
demo1:继承Thread类,重写run()方法
package thread_test;
public class ThreadDemo1 extends Thread {
ThreadDemo1(){
}
ThreadDemo1(String szName){
super(szName);
}
//重载run函数
public void run() {
for(int count = 1 , row = 1 ; row < 10 ; row ++ , count ++) {
for(int i = 0 ; i < count ; i ++) {
System.out.print("*");
}
System.out.println();
}
}
public static void main(String[] args) {
//线程赛跑
ThreadDemo1 td1 = new ThreadDemo1();
ThreadDemo1 td2 = new ThreadDemo1();
ThreadDemo1 td3 = new ThreadDemo1();
td1.start();
td2.start();
td3.start();
}
}
demo2:实现runnable接口,实现run()方法
package thread_test;
public class ThreadDemo2 implements Runnable{
public void run() {
for(int count = 1 , row = 1 ; row < 10 ; row ++ , count ++) {
for(int i = 0 ; i < count ; i ++) {
System.out.print("*");
}
System.out.println();
}
}
public static void main(String[] args) {
//存在线程赛跑问题
Runnable rb1 = new ThreadDemo2();
Runnable rb2 = new ThreadDemo2();
Runnable rb3 = new ThreadDemo2();
Thread td1 = new Thread(rb1);
Thread td2 = new Thread(rb2);
Thread td3 = new Thread(rb3);
td1.start();
td2.start();
td3.start();
}
}
demo3:两种方法解决进程赛跑问题
package thread_test; //两种方法解决线程赛跑
class ThreadWait extends Thread{ public ThreadWait() { } public ThreadWait(String name) {
super(name);
} @Override
public void run() {
for(int count = 1 , row = 1 ; row < 10 ; row ++ , count ++) {
for(int i = 0 ; i < count ; i ++) {
System.out.print("*");
}
System.out.println();
}
}
} public class ThreadDemo3{
public static void main(String[] args) {
ThreadDemo3 td = new ThreadDemo3();
// td.Method1();
td.Method2();
} public void Method1() {
ThreadWait tw1 = new ThreadWait();
ThreadWait tw2 = new ThreadWait();
tw1.start();
while(tw1.isAlive()) {
try{
Thread.sleep(100);
}catch(Exception e){
e.getMessage();
}
}
tw2.start();
} public void Method2() {
ThreadWait tw1 = new ThreadWait();
ThreadWait tw2 = new ThreadWait();
tw1.start();
try {
tw1.join(); // 等待该线程中止
}catch(Exception e){
e.toString();
}
tw2.start();
}
}
线程异步访问数据导致问题:
package thread_test; //线程异步访问数据导致问题
class ShareData{
public static String szData = "";
} class ThreadDemo extends Thread{ private static ShareData oShare; ThreadDemo(){
} ThreadDemo(String name, ShareData oShare){
super(name);
this.oShare = oShare;
} public void run() {
for(int i = 0 ; i < 5 ; i ++) {
if(this.getName().equals("th1")) {
oShare.szData = "这是第一个进程";
try {
Thread.sleep(100);
}catch(Exception e) { }
System.out.println(this.getName() + oShare.szData);
}else if(this.getName().equals("th2")) {
oShare.szData = "这是第二个进程";
try {
Thread.sleep(100);
}catch(Exception e) { }
System.out.println(this.getName() + oShare.szData);
}
}
}
} public class ThreadDemo5 { public static void main(String[] args) {
ShareData oShare = new ShareData();
ThreadDemo th1 = new ThreadDemo("th1", oShare);
ThreadDemo th2 = new ThreadDemo("th2", oShare);
th1.start();
th2.start();
}
}
得到的结果并不是我们想要的:

解决办法:
通过“锁”解决线程赛跑问题并实现多线程数据同步:
package thread_test;
class ShareData0{
public static String szData = "";
} class ThreadDemo0 extends Thread{ private static ShareData0 oShare; ThreadDemo0(){
} ThreadDemo0(String name, ShareData0 oShare){
super(name);
this.oShare = oShare;
} public void run() {
//同步快,并指出同步数据oShare
synchronized(oShare){
for(int i = 0 ; i < 5 ; i ++) {
if(this.getName().equals("th1")) {
oShare.szData = "这是第一个进程";
try {
Thread.sleep(100);
}catch(Exception e) { }
System.out.println(this.getName() + oShare.szData);
}else if(this.getName().equals("th2")) {
oShare.szData = "这是第二个进程";
try {
Thread.sleep(100);
}catch(Exception e) { }
System.out.println(this.getName() + oShare.szData);
}
}
}
}
}
public class ThreadDemo6 { public static void main(String[] args) {
ShareData0 oShare = new ShareData0();
ThreadDemo0 th1 = new ThreadDemo0("th1", oShare);
ThreadDemo0 th2 = new ThreadDemo0("th2", oShare); th1.start();
th2.start();
}
}
得到结果:

死锁:由于两个线程都在等待对方释放各自拥有的锁的现象称为死锁,这种现象往往是由于相互潜逃的synchronized代码段而造成的,所以少用synchronized嵌套。
下面是一个死锁的例子:
package thread_test;
public class LockedThread extends Thread{
private static Object A = new Object();
private static Object B = new Object();
private static boolean flag = true;
public static void main(String[] args) {
LockedThread th1 = new LockedThread();
LockedThread th2 = new LockedThread();
th1.start();
th2.start();
}
public void AccessA() {
flag = false;
synchronized(A) {
System.out.println("th1获得了A的锁");
try {
Thread.sleep(1000);
}catch(Exception e) {
}
System.out.println("th1还想要B的锁");
synchronized(B) {
System.out.println("th1获得了B的锁");
}
}
}
public void AccessB() {
flag = true;
synchronized(B) {
System.out.println("th2获得了B的锁");
try {
Thread.sleep(1000);
}catch(Exception e) {
}
System.out.println("th2还想要A的锁");
synchronized(A) {
System.out.println("th2获得了A的锁");
}
}
}
public void run(){
if(flag) {
AccessA();
}else {
AccessB();
}
}
}
显示结果:

程序没有结束 而是停在了这里,这就是死锁。
java——多线程的实现方式、三种办法解决线程赛跑、多线程数据同步(synchronized)、死锁的更多相关文章
- QThread 爬坑之旅(三种办法解决QObject: Cannot create children for a parent that is in a different thread)
Cannot create children for a parent that is in a different thread. 在Qt的官方文档,大家知道有两种方式使用QThread. You ...
- Java通过JDBC连接数据库的三种方式!!!并对数据库实现增删改查
前言 java连接数据库完整流程为: 1,获得驱动(driver),数据库连接(url),用户名(username),密码(password)基本信息的三种方式. 2,通过获得的信息完成JDBC实现连 ...
- java 实现md5加密的三种方式与解密
java 实现md5加密的三种方式 CreateTime--2018年5月31日15点04分 Author:Marydon 一.解密 说明:截止文章发布,Java没有实现解密,但是已有网站可以免费 ...
- Java连接Oracle数据库的三种连接方式
背景: 这两天在学习Oracle数据库,这里就总结下自己上课所学的知识,同时记录下来,方便整理当天所学下的知识,也同时方便日后自己查询. SQL语句的话,这里我就不多讲了,感觉和其他的数据库(MySQ ...
- Java遍历List集合的三种方法
Java遍历List集合的三种方法 List<String> list = new ArrayList<String>(); list.add("aaa") ...
- PHP修改memory_limit的三种办法
PHP修改memory_limit的三种办法 2010-06-11 10:57:11 分类: 可能是分词程序的问题.只要搜索的字段达到十个汉字以上,就会出现诸如以下的错误 Fatal error: ...
- C++ 继承方式 //语法:class 子类 :继承方式 父类 //继承方式 三种: //1.公共继承 //2.保护继承 //3.私有继承
1 //继承方式 2 //语法:class 子类 :继承方式 父类 3 //继承方式 三种: 4 //1.公共继承 5 //2.保护继承 6 //3.私有继承 7 8 #include <ios ...
- 三种方法解决android帮助文档打开慢
三种方法解决android帮助文档打开慢 经查是因为本地文档中的网页有如下两段js代码会联网加载信息,将其注释掉后就好了 <link rel="stylesheet" h ...
- C2B电商三种主要模式的分析_数据分析师
C2B电商三种主要模式的分析_数据分析师 在过去的一年中电商领域血雨腥风,尤其是天猫.京东.苏宁.当当.易讯等B2C电商打得不亦乐乎.而随着B2C领域竞争进入白热化阶段,C2B模式也在天猫" ...
随机推荐
- Qt嵌入式开发环境搭建
一.Qt版本介绍 按照不同的图形界面来划分,分为四个版本: 1.Win32版:适用于windows平台 2.X11版:适用于各种X系统的Linux和Unix平台 3.Mac版:适用于苹果的MacOS ...
- GCD 学习(二)dispatch_queue_create创建Dispatch Queue
摘录于: http://zhuyanfeng.com/archives/3042 dispatch_queue_create 用于创建用户线程队列.可以创建Serial/Concurrent Disp ...
- 数据结构_calculator
问题描述 小 V 发明了一个神奇的整数计算器:给定一个合法的表达式,这个计算器能求出这个表达式的最终答案.表达式可能包含:+:运算符,整数加法.如 1+1=2-:运算符,整数减法.如 1-1=0*:运 ...
- windows脚本设置网络IP地址
需求描述 不通的网络环境下,可能需要设置静态IP地址,或设置为动态获取,每次重复手动的配置费时费力,通过脚本可以实现一键设置 脚本实现 1.设置静态IP 1.1新建文本文档,复制粘贴如下内容 nets ...
- 初探webapi
在网上看了小牛之路的webapi那篇文章,所以自己也想偿试一下 一,webapi简介 目前使用Web服务的三种主流的方式是:远程过程调用(RPC),面向服务架构(SOA)以及表征性状态转移(REST) ...
- SQL server 提取字符中第一次和最后一次出现的数字
CREATE FUNCTION [dbo].[StringExtractNumber(FirstOrLast)](@address nvarchar(max),@firstOrLast INT) re ...
- 692. Top K Frequent Words
Given a non-empty list of words, return the k most frequent elements. Your answer should be sorted b ...
- nginx: [emerg] the "ssl" parameter requires ngx_http_ssl_module in /usr/local/nginx//conf/nginx.conf:117
SSL相关的配置加到了nginx的配置文件中后,nginx竟然启动不起来了 于是用如下命令测试问题所在: /usr/local/nginx/sbin/nginx -c /usr/local/nginx ...
- Linux基础学习(二)
前言: 我们在上一节了解了一下linux的硬件组成,虽然也许对具体的东西还不甚了解,但是我们知道了linux下一切皆文件这一特性 我们装好了CentOS7的虚拟机(这个可以看别人教程来装起来,比较简单 ...
- 关于vue项目多页面的配置
基于vue2.0生成项目,一段时间都在找如何配置成多个页面的.网上有这样的例子相对也是比较详细的,但是还是有些许不一样的地方的.所以,我还是记录下来,当然我也是参考了网上的资料的. 当然先来个vue的 ...