JAVA 多线程
目录[ Hide ]
多线程的引入
多线程并行和并发的区别
Java程序运行原理和JVM的启动是多线程的吗
package com.heima.thread;
/**
* Code by pureqh on 2021-03-03
*/
public class Demo1_Thread {
public static void main(String[] args) {
for (int i = 0; i <100000000 ; i++) {
new Demo();
}
for (int i = 0; i <1000000 ; i++) {
System.out.println("我是主线程的执行代码");
}
}
}
class Demo{
@Override
public void finalize() {
System.out.println("垃圾被回收了");
}
}
/**
* Code by pureqh on 2021-03-03
*/
public class Demo1_Thread {
public static void main(String[] args) {
for (int i = 0; i <100000000 ; i++) {
new Demo();
}
for (int i = 0; i <1000000 ; i++) {
System.out.println("我是主线程的执行代码");
}
}
}
class Demo{
@Override
public void finalize() {
System.out.println("垃圾被回收了");
}
}
多线程程序实现的方式1
应将多线程代码放置run方法 然后调用start方法启用多线程
package com.heima.thread;
/**
* Code by pureqh on 2021-03-03
*/
public class Demo2_Thread {
public static void main(String[] args) {
MyThread mt = new MyThread(); //创建线程的子类对象
mt.start(); //开启线程
for (int i = 0; i <100 ; i++) {
System.out.println("bbb");
}
}
}
class MyThread extends Thread{ //继承Thread
public void run(){ //重写run方法
for (int i = 0; i <1000 ; i++) { //将要执行的方法写到run方法中
System.out.println("aa");
}
}
}
/**
* Code by pureqh on 2021-03-03
*/
public class Demo2_Thread {
public static void main(String[] args) {
MyThread mt = new MyThread(); //创建线程的子类对象
mt.start(); //开启线程
for (int i = 0; i <100 ; i++) {
System.out.println("bbb");
}
}
}
class MyThread extends Thread{ //继承Thread
public void run(){ //重写run方法
for (int i = 0; i <1000 ; i++) { //将要执行的方法写到run方法中
System.out.println("aa");
}
}
}
多线程程序实现的方式2
package com.heima.thread;
/**
* Code by pureqh on 2021-03-03
*/
public class Demo3_Thread {
public static void main(String[] args) {
MyRunnable mr = new MyRunnable(); //创建Runnable的子类对象
Thread t = new Thread(mr); //将其当作参数传递给thread的构造函数
t.start(); //开启线程
for (int i = 0; i <100 ; i++) {
System.out.println("bb");
}
}
}
class MyRunnable implements Runnable{ //定义一个类实现runnable接口
@Override
public void run() { //重写run方法
for (int i = 0; i <1000 ; i++) { //将要执行的方法写到run方法中
System.out.println("aa");
}
}
}
/**
* Code by pureqh on 2021-03-03
*/
public class Demo3_Thread {
public static void main(String[] args) {
MyRunnable mr = new MyRunnable(); //创建Runnable的子类对象
Thread t = new Thread(mr); //将其当作参数传递给thread的构造函数
t.start(); //开启线程
for (int i = 0; i <100 ; i++) {
System.out.println("bb");
}
}
}
class MyRunnable implements Runnable{ //定义一个类实现runnable接口
@Override
public void run() { //重写run方法
for (int i = 0; i <1000 ; i++) { //将要执行的方法写到run方法中
System.out.println("aa");
}
}
}
实现Runnable的原理
Runnable内部将子类对象引用了run方法
两种方式的区别
匿名内部类实现线程的两种方式
package com.heima.thread;
/**
* Code by pureqh on 2021-03-03
*/
public class Demo4_Thread {
public static void main(String[] args) {
new Thread(){ //继承Thread类
public void run(){ //重写run方法
for (int i = 0; i <100 ; i++) { //将要执行的代码写在run方法中
System.out.println("a");
}
}
}.start(); //开启线程
new Thread(new Runnable(){ //将Runnable的子类对象传递给Thread的构造方法
public void run(){ //重写run方法
for (int i = 0; i <100 ; i++) { //将要执行的代码写在run方法中
System.out.println("b");
}
}
}).start();
}
}
/**
* Code by pureqh on 2021-03-03
*/
public class Demo4_Thread {
public static void main(String[] args) {
new Thread(){ //继承Thread类
public void run(){ //重写run方法
for (int i = 0; i <100 ; i++) { //将要执行的代码写在run方法中
System.out.println("a");
}
}
}.start(); //开启线程
new Thread(new Runnable(){ //将Runnable的子类对象传递给Thread的构造方法
public void run(){ //重写run方法
for (int i = 0; i <100 ; i++) { //将要执行的代码写在run方法中
System.out.println("b");
}
}
}).start();
}
}
获取名字和设置名字
package com.heima.threadmethod;
/**
* Code by pureqh on 2021-03-03
*/
public class Demo1_Name {
public static void main(String[] args) {
demo1();
Thread t1 = new Thread(){
public void run(){
//this.setName("烙亡");
System.out.println(this.getName()+".....aaa");
}
};
t1.setName("laowang");
t1.start();
}
/*通过构造方法给name赋值*/
private static void demo1() {
new Thread("嫪辋"){
public void run(){
System.out.println(this.getName()+".....aaa");
}
}.start();
}
}
/**
* Code by pureqh on 2021-03-03
*/
public class Demo1_Name {
public static void main(String[] args) {
demo1();
Thread t1 = new Thread(){
public void run(){
//this.setName("烙亡");
System.out.println(this.getName()+".....aaa");
}
};
t1.setName("laowang");
t1.start();
}
/*通过构造方法给name赋值*/
private static void demo1() {
new Thread("嫪辋"){
public void run(){
System.out.println(this.getName()+".....aaa");
}
}.start();
}
}
获取当前线程的对象
currentThread()
package com.heima.threadmethod;
/**
* Code by pureqh on 2021-03-03
*/
public class Demo2_CurrentThread {
public static void main(String[] args) {
new Thread(){
public void run(){
System.out.println(getName()+"...aaa");
}
}.start();
new Thread(new Runnable(){
public void run(){
System.out.println(Thread.currentThread().getName()+"...bb");
}
}).start();
Thread.currentThread().setName("主线程");
System.out.println(Thread.currentThread().getName());
}
}
/**
* Code by pureqh on 2021-03-03
*/
public class Demo2_CurrentThread {
public static void main(String[] args) {
new Thread(){
public void run(){
System.out.println(getName()+"...aaa");
}
}.start();
new Thread(new Runnable(){
public void run(){
System.out.println(Thread.currentThread().getName()+"...bb");
}
}).start();
Thread.currentThread().setName("主线程");
System.out.println(Thread.currentThread().getName());
}
}
休眠线程
sleep()
package com.heima.threadmethod;
/**
* Code by pureqh on 2021-03-03
*/
public class Demo3_Sleep {
public static void main(String[] args) throws InterruptedException {
//demo1();
new Thread(){
public void run(){
for (int i = 20; i >=0 ; i--) {
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println(getName()+"..bb");
}
}
}.start();
}
private static void demo1() throws InterruptedException {
for (int i = 20; i >=0 ; i--) {
Thread.sleep(1000);
System.out.println("倒计时"+i+"秒");
}
}
}
/**
* Code by pureqh on 2021-03-03
*/
public class Demo3_Sleep {
public static void main(String[] args) throws InterruptedException {
//demo1();
new Thread(){
public void run(){
for (int i = 20; i >=0 ; i--) {
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println(getName()+"..bb");
}
}
}.start();
}
private static void demo1() throws InterruptedException {
for (int i = 20; i >=0 ; i--) {
Thread.sleep(1000);
System.out.println("倒计时"+i+"秒");
}
}
}
守护线程
setDaemon()
package com.heima.threadmethod;
/**
* Code by pureqh on 2021-03-03
*/
public class Demo4_Daemon {
public static void main(String[] args) {
Thread t1 = new Thread("老大"){
public void run(){
for (int i = 0; i < 2; i++) {
System.out.println(getName()+"...aa");
}
}
};
Thread t2 = new Thread("老二"){
public void run(){
for (int i = 0; i < 50; i++) {
System.out.println(getName()+"...bb");
}
}
};
t2.setDaemon(true); //当传入true意味着设置为守护进程
t1.start();
t2.start();
}
}
/**
* Code by pureqh on 2021-03-03
*/
public class Demo4_Daemon {
public static void main(String[] args) {
Thread t1 = new Thread("老大"){
public void run(){
for (int i = 0; i < 2; i++) {
System.out.println(getName()+"...aa");
}
}
};
Thread t2 = new Thread("老二"){
public void run(){
for (int i = 0; i < 50; i++) {
System.out.println(getName()+"...bb");
}
}
};
t2.setDaemon(true); //当传入true意味着设置为守护进程
t1.start();
t2.start();
}
}
有时候会出现守不住的情况 因为cpu速度过快 导致指令出现缓冲时间 所以可能漏几个。
加入线程
join()
package com.heima.threadmethod;
/**
* Code by pureqh on 2021-03-03
*/
public class Demo5_Join {
public static void main(String[] args) {
final Thread t1 = new Thread(){
public void run(){
for (int i = 0; i < 10 ; i++) {
System.out.println(getName()+"...aa");
}
}
};
Thread t2 = new Thread(){
public void run(){
for (int i = 0; i < 10 ; i++) {
if (i == 2){
try {
t1.join(1); //插队指定的时间,过了指定的时间后,两条线程交替执行
} catch (InterruptedException e) {
e.printStackTrace();
}
}
System.out.println(getName()+"...bbbbbbbb");
}
}
};
t1.start();
t2.start();
}
}
/**
* Code by pureqh on 2021-03-03
*/
public class Demo5_Join {
public static void main(String[] args) {
final Thread t1 = new Thread(){
public void run(){
for (int i = 0; i < 10 ; i++) {
System.out.println(getName()+"...aa");
}
}
};
Thread t2 = new Thread(){
public void run(){
for (int i = 0; i < 10 ; i++) {
if (i == 2){
try {
t1.join(1); //插队指定的时间,过了指定的时间后,两条线程交替执行
} catch (InterruptedException e) {
e.printStackTrace();
}
}
System.out.println(getName()+"...bbbbbbbb");
}
}
};
t1.start();
t2.start();
}
}
礼让线程
yield让出cpu
其实很多情况下达不到理论中的效果
package com.heima.threadmethod;
/**
* Code by pureqh on 2021-03-03
*/
public class Demo6_Yield {
public static void main(String[] args) {
new MyThread().start();
new MyThread().start();
}
}
class MyThread extends Thread{
public void run(){
for (int i = 0; i <1000 ; i++) {
if (i % 10 == 0){
Thread.yield(); //让出cpu
}
System.out.println(getName()+"..."+i);
}
}
}
/**
* Code by pureqh on 2021-03-03
*/
public class Demo6_Yield {
public static void main(String[] args) {
new MyThread().start();
new MyThread().start();
}
}
class MyThread extends Thread{
public void run(){
for (int i = 0; i <1000 ; i++) {
if (i % 10 == 0){
Thread.yield(); //让出cpu
}
System.out.println(getName()+"..."+i);
}
}
}
设置线程的优先级
package com.heima.threadmethod;
/**
* Code by pureqh on 2021-03-03
*/
public class Demo7_Priority {
public static void main(String[] args) {
Thread t1 = new Thread(){
public void run(){
for (int i = 0; i < 1000; i++) {
System.out.println(getName()+"...aa");
}
}
};
Thread t2 = new Thread(){
public void run(){
for (int i = 0; i < 1000; i++) {
System.out.println(getName()+"...bbbbbbbb");
}
}
};
t1.setPriority(10);
t2.setPriority(1);
t1.start();
t2.start();
}
}
/**
* Code by pureqh on 2021-03-03
*/
public class Demo7_Priority {
public static void main(String[] args) {
Thread t1 = new Thread(){
public void run(){
for (int i = 0; i < 1000; i++) {
System.out.println(getName()+"...aa");
}
}
};
Thread t2 = new Thread(){
public void run(){
for (int i = 0; i < 1000; i++) {
System.out.println(getName()+"...bbbbbbbb");
}
}
};
t1.setPriority(10);
t2.setPriority(1);
t1.start();
t2.start();
}
}
同步代码块
package com.heima.syn;
/**
* Code by pureqh on 2021-03-03
*/
public class Demo1_Synchronized {
public static void main(String[] args) {
final Printer p = new Printer();
new Thread(){
public void run(){
while (true){
p.printl1();
}
}
}.start();
new Thread(){
public void run(){
while (true){
p.printl2();
}
}
}.start();
}
}
class Printer{
Demo d = new Demo();
public void printl1(){
synchronized (d){ //锁对象可以是任意的
System.out.println("穷");
System.out.println("其");
System.out.println("道");
System.out.println("者");
System.out.println("\r\n");
}
}
public void printl2(){
synchronized (d){
System.out.println("归");
System.out.println("处");
System.out.println("亦");
System.out.println("同");
System.out.println("\r\n");
}
}
}
class Demo{
}
/**
* Code by pureqh on 2021-03-03
*/
public class Demo1_Synchronized {
public static void main(String[] args) {
final Printer p = new Printer();
new Thread(){
public void run(){
while (true){
p.printl1();
}
}
}.start();
new Thread(){
public void run(){
while (true){
p.printl2();
}
}
}.start();
}
}
class Printer{
Demo d = new Demo();
public void printl1(){
synchronized (d){ //锁对象可以是任意的
System.out.println("穷");
System.out.println("其");
System.out.println("道");
System.out.println("者");
System.out.println("\r\n");
}
}
public void printl2(){
synchronized (d){
System.out.println("归");
System.out.println("处");
System.out.println("亦");
System.out.println("同");
System.out.println("\r\n");
}
}
}
class Demo{
}
同步方法
package com.heima.syn;
/**
* Code by pureqh on 2021-03-03
*/
public class Demo2_Synchronized {
public static void main(String[] args) {
final Printer p = new Printer();
new Thread(){
public void run(){
while (true){
p.printl1();
}
}
}.start();
new Thread(){
public void run(){
while (true){
p.printl2();
}
}
}.start();
}
}
class Printer1{
Demo1 d = new Demo1();
//非静态的同步方法的锁对象是什么 他们不是同一个锁 非静态的同步方法锁对象是this
//public synchronized void printl1(){ //同步方法只需要在方法上加synchronized 关键字即可
public static synchronized void print1(){ //静态的同步方法的锁对象是该类的字节码对象 类名.class
//synchronized (d){ //锁对象可以是任意的 锁对象不能用匿名对象 因为匿名对象不是同一个对象
System.out.println("穷");
System.out.println("其");
System.out.println("道");
System.out.println("者");
System.out.println("\r\n");
//}
}
//public void printl2(){
public static void printl2(){
//synchronized (d){
synchronized (Printer1.class){
System.out.println("归");
System.out.println("处");
System.out.println("亦");
System.out.println("同");
System.out.println("\r\n");
}
}
}
class Demo1{
}
/**
* Code by pureqh on 2021-03-03
*/
public class Demo2_Synchronized {
public static void main(String[] args) {
final Printer p = new Printer();
new Thread(){
public void run(){
while (true){
p.printl1();
}
}
}.start();
new Thread(){
public void run(){
while (true){
p.printl2();
}
}
}.start();
}
}
class Printer1{
Demo1 d = new Demo1();
//非静态的同步方法的锁对象是什么 他们不是同一个锁 非静态的同步方法锁对象是this
//public synchronized void printl1(){ //同步方法只需要在方法上加synchronized 关键字即可
public static synchronized void print1(){ //静态的同步方法的锁对象是该类的字节码对象 类名.class
//synchronized (d){ //锁对象可以是任意的 锁对象不能用匿名对象 因为匿名对象不是同一个对象
System.out.println("穷");
System.out.println("其");
System.out.println("道");
System.out.println("者");
System.out.println("\r\n");
//}
}
//public void printl2(){
public static void printl2(){
//synchronized (d){
synchronized (Printer1.class){
System.out.println("归");
System.out.println("处");
System.out.println("亦");
System.out.println("同");
System.out.println("\r\n");
}
}
}
class Demo1{
}
线程安全问题
package com.heima.syn;
import org.omg.Messaging.SyncScopeHelper;
/**
* Code by pureqh on 2021-03-04
* 铁路售票,一共100张,通过四个窗口卖完
*/
public class Demo3_Ticker {
public static void main(String[] args) {
new Ticket().start();
new Ticket().start();
new Ticket().start();
new Ticket().start();
}
}
class Ticket extends Thread{
private static int ticket = 100;
private static Object obj = new Object(); //如果用引用数据类型成员变量当作锁对象,必须是静态的
public void run(){
while (true){
synchronized (Ticket.class) {
if (ticket == 0) {
break;
}
try {
Thread.sleep(10);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println(getName() + "这是第" + ticket-- + "号票");
}
}
}
}
import org.omg.Messaging.SyncScopeHelper;
/**
* Code by pureqh on 2021-03-04
* 铁路售票,一共100张,通过四个窗口卖完
*/
public class Demo3_Ticker {
public static void main(String[] args) {
new Ticket().start();
new Ticket().start();
new Ticket().start();
new Ticket().start();
}
}
class Ticket extends Thread{
private static int ticket = 100;
private static Object obj = new Object(); //如果用引用数据类型成员变量当作锁对象,必须是静态的
public void run(){
while (true){
synchronized (Ticket.class) {
if (ticket == 0) {
break;
}
try {
Thread.sleep(10);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println(getName() + "这是第" + ticket-- + "号票");
}
}
}
}
火车站卖票的例子用实现Runnable接口
package com.heima.syn;
/**
* Code by pureqh on 2021-03-04
* 火车站卖票实现runnable接口
*/
public class Demo4_Ticket {
public static void main(String[] args) {
MyTicket mt = new MyTicket();
new Thread(mt).start();
new Thread(mt).start();
new Thread(mt).start();
new Thread(mt).start();
}
}
class MyTicket implements Runnable{
private int ticket = 100;
@Override
public void run() {
while (true){
synchronized (MyTicket.class) {
if (ticket == 0) {
break;
}
try {
Thread.sleep(10);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println(Thread.currentThread().getName() + "这是第" + ticket-- + "号票");
}
}
}
}
/**
* Code by pureqh on 2021-03-04
* 火车站卖票实现runnable接口
*/
public class Demo4_Ticket {
public static void main(String[] args) {
MyTicket mt = new MyTicket();
new Thread(mt).start();
new Thread(mt).start();
new Thread(mt).start();
new Thread(mt).start();
}
}
class MyTicket implements Runnable{
private int ticket = 100;
@Override
public void run() {
while (true){
synchronized (MyTicket.class) {
if (ticket == 0) {
break;
}
try {
Thread.sleep(10);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println(Thread.currentThread().getName() + "这是第" + ticket-- + "号票");
}
}
}
}