Java并发(多线程)
一、多线程的基本概念
1.什么是进程、多进程有什么作用?
大家都使用计算机,当我们打开某一个软件的时候,其实就是启动了一个进程,可以打开任务管理器看看,我们打开的每一个软件,都是一个进程,在同一个操作系统中,可以同时启动多个进程。
单进程计算机只能在一个时间内做一件事情。在我们打开办公软件的的时候,也可以同时听歌,为什么呢?不是只能做一件事情吗,这是因为操作系统将cpu的时间片分配给了每一个进程,让我们感觉是并行处理的。
多进程不是为了提高执行速度,是为了提高CPU使用率,具体只是可以去学习操作系统进行了解
进程与进程之间是独立的
2.什么是线程,多线程有什么作用?
线程是进程中的一个执行场景,他们是共享数据的(堆内存和方法区内存、栈内存是独立的),一个线程一个栈
与进程相比,线程更轻量级,创建、撤销一个线程比启动新进行的开销要小得多
3.java程序的运行原理
java命令会启动Java虚拟机,启动JVM,等于启动了一个应用程序,表示启动了一个进程,该进程会自动自动一个“主线程”,然后主线程去调用某个类的main方法,所以main方法运行在主线程中,在此之前所有的程序都是单线程的。
二、线程的创建和启动
1、继承Thread类
public class Test{
public static void main(String[] args) {
Person person = new Person();
person.start(); //start不是马上执行,而是使线程进入就绪,真正执行是由JAVA的线程调度机制来完成
for(int i=0; i<10; i++){
System.out.println("main ->" + i);
}
}
}
class Person extends Thread{
public void run(){
for(int i=0; i<30; i++){
System.out.println("run ->" +i);
}
}
}
2、实现Runnable接口(推荐)
public class Test{
public static void main(String[] args) {
Person person = new Person();
Thread t = new Thread(person);
t.start();
for(int i=0; i<10; i++){
System.out.println("main ->" + i);
}
}
}
class Person implements Runnable{
public void run(){
for(int i=0; i<30; i++){
System.out.println("run ->" +i);
}
}
}
由于Runnable是一个函数式接口,可以用lamda表达式建立一个实例:
Runnable r = () ->{...};
三、线程的生命周期

这是网上找的图
初始状态:新创建一个线程对象
可运行状态:也就是就绪状态,调用start()方法后,该线程有权利获取cpu时间片
运行状态:获取到cpu时间片后开始运行,如果这次没有运行完,下一次接着运行,不是从头开始
阻塞状态:因为某种原因放弃了cpu的使用权,暂时停止运行,直到线程调度器重新激活它
死亡状态:线程执行完了或因异常退出了run方法
方法比较:
- Thread.sleep(long millis),一定是当前线程调用此方法,当前线程进入TIME_WAITING状态,但不释放对象锁,millis后线程自动苏醒进入就绪状态。作用:给其它线程执行机会的最佳方式。
- Thread.yield(),一定是当前线程调用此方法,当前线程放弃获取的cpu时间片,由运行状态变会就绪状态,让OS再次选择线程。作用:让相同优先级的线程轮流执行,但并不保证一定会轮流执行。实际中无法保证yield()达到让步目的,因为让步的线程还有可能被线程调度程序再次选中。Thread.yield()不会导致阻塞。
- t.join()/t.join(long millis),当前线程里调用其它线程t的join方法,当前线程进入TIME_WAITING/TIME_WAITING状态,当前线程不释放已经持有的对象锁。线程t执行完毕或者millis时间到,当前线程进入就绪状态。
- obj.wait(),当前线程调用对象的wait()方法,当前线程释放对象锁,进入等待队列。依靠notify()/notifyAll()唤醒或者wait(long timeout)timeout时间到自动唤醒。
- obj.notify()唤醒在此对象监视器上等待的单个线程,选择是任意性的。notifyAll()唤醒在此对象监视器上等待的所有线程。
为什么弃用stop和suspend方法?
stop方法天生就不安全,当线程被终止,立即释放对象锁,这会导致对象处于不一致的状态。例如:在转账的时候,钱已转出,对方还没到账,对象锁已经被破坏;当线程要终止另一个线程的时候,无法知道什么时候调用stop方法是安全的,什么时候导致对象被破坏
在看suspend,和stop不同,suspend不会破坏对象,但是如果用suspend挂起一个持有一个锁的线程,该锁在恢复之前是不可用的,如果要调用suspend方法的线程试图获得同一个锁,那么程序死锁;被挂起的线程等着被恢复,而将其挂起的线程等待获得锁
补一张图(牛客上看见的):

Java并发(多线程)的更多相关文章
- java并发多线程显式锁Condition条件简介分析与监视器 多线程下篇(四)
Lock接口提供了方法Condition newCondition();用于获取对应锁的条件,可以在这个条件对象上调用监视器方法 可以理解为,原本借助于synchronized关键字以及锁对象,配备了 ...
- java 并发多线程 锁的分类概念介绍 多线程下篇(二)
接下来对锁的概念再次进行深入的介绍 之前反复的提到锁,通常的理解就是,锁---互斥---同步---阻塞 其实这是常用的独占锁(排它锁)的概念,也是一种简单粗暴的解决方案 抗战电影中,经常出现为了阻止日 ...
- java 并发多线程显式锁概念简介 什么是显式锁 多线程下篇(一)
目前对于同步,仅仅介绍了一个关键字synchronized,可以用于保证线程同步的原子性.可见性.有序性 对于synchronized关键字,对于静态方法默认是以该类的class对象作为锁,对于实例方 ...
- Java并发多线程 - 并发工具类JUC
安全共享对象策略 1.线程限制 : 一个被线程限制的对象,由线程独占,并且只能被占有它的线程修改 2.共享只读 : 一个共享只读的对象,在没有额外同步的情况下,可以被多个线程并发访问, 但是任何线程都 ...
- Java并发/多线程系列——初识篇
回到过去,电脑有一个CPU,一次只能执行一个程序.后来多任务处理意味着计算机可以同时执行多个程序(AKA任务或进程).这不是真的"同时".单个CPU在程序之间共享.操作系统将在运行 ...
- day 04 Java并发多线程
http://www.cnblogs.com/hellocsl/p/3969768.html?utm_source=tuicool&utm_medium=referralPS:而JVM 每遇到 ...
- Java并发(一)Java并发/多线程教程
在过去一台电脑只有单个CPU,并且在同一时间只能执行单个程序.后来出现的"多任务"意味着电脑在可以同时执行多个程序(AKA任务或者进程).虽然那并不是真正意义上的"同时& ...
- Java并发多线程面试题 Top 50
不管你是新程序员还是老手,你一定在面试中遇到过有关线程的问题.Java语言一个重要的特点就是内置了对并发的支持,让Java大受企业和程序员的欢迎.大多数待遇丰厚的Java开发职位都要求开发者精通多线程 ...
- Java并发-多线程面试(全面)
1. 什么是线程?2. 什么是线程安全和线程不安全?3. 什么是自旋锁?4. 什么是Java内存模型?5. 什么是CAS?6. 什么是乐观锁和悲观锁?7. 什么是AQS?8. 什么是原子操作?在Jav ...
- java并发多线程(摘自网络)
1. 进程和线程之间有什么不同? 一个进程是一个独立(self contained)的运行环境,它可以被看作一个程序或者一个应用.而线程是在进程中执行的一个任务.Java运行环境是一个包含了不同的类和 ...
随机推荐
- luogu P1710 地铁涨价
嘟嘟嘟 一道最短路好题. 首先明确一点,把一条边的边权变成2,等于删去这条边.因为变成2后最短路肯定不会经过这条边,就相当于删去这条边了. 所以题目变成了依次删去Q条边,求每一次删完边后有几个点的最短 ...
- openfiles_(命令)查看已打开的文件列表
效果: 功能: 查看Windows系统的进程信息,包括进程打开了哪些文件 描述: 允许管理员列出系统上已打开的文件和文件夹或与其断开连接. 参数列表: /Disconnect 中断至少一个打开的文件的 ...
- 0.Python 爬虫之Scrapy入门实践指南(Scrapy基础知识)
目录 0.0.Scrapy基础 0.1.Scrapy 框架图 0.2.Scrapy主要包括了以下组件: 0.3.Scrapy简单示例如下: 0.4.Scrapy运行流程如下: 0.5.还有什么? 0. ...
- 【转】不错的linux下通用的java程序启动脚本
虽然写起动shell的频率非常不高...但是每次要写都要对付一大堆的jar文件路径,新加jar包也必须要修改起动shell. 在网上找到一个挺好的通用shell脚本. 只需要修改一些配置变量,就可以用 ...
- ES6学习笔记(对象)
1.属性的简洁表示法 const foo = 'bar'; const baz = {foo}; baz // {foo: "bar"} // 等同于 const baz = {f ...
- php常见的几种排序以及二分法查找
<?php 1.插入排序 思想: 每次将一个待排序的数据元素插入到前面已经排好序的数列中,使数列依然有序,知道待排序数据元素全部插入完为止. 示例: [初始关键字] [49] 38 65 97 ...
- WebStorm中Node.js项目配置教程——项目设置
上一章讲解了Node.js项目在WebStorm中的两种创建方式,当完成Node.js项目创建以后,剩下的就是涉及配置设置工作. 为了确保Node.js全局和Node.js核心模块的代码完成功能,打开 ...
- kinect v2
http://www.tuicool.com/articles/NbmyyeU https://channel9.msdn.com/Blogs/raw-tech/Making-your-body-th ...
- 火狐 SSL 收到了一个弱临时 Diffie-Hellman 密钥
火狐 SSL 收到了一个弱临时 Diffie-Hellman 密钥 最近在用FireFox 调试时使用Https,连接 https网址 时发生错误. 在服务器密钥交换握手信息中 SSL 收到了一个 ...
- 分享一个带有合计行功能的DataGridView扩展
因为一个Winform的项目中需要用到带有合计行的表格,并且需要满足以下需求: 合计行可自动对需要求和的列进行求和计算; 合计行必须固定(冻结)在表格的最底部,且其位置不受滚动条的滚动而移动; 可以设 ...