总结
线程
线程:执行的独立代码
线程执行是靠cpu分配时间片,同一个时间片上只能执行一个线程
线程的状态:
- 新建
- 就绪
- 运行
- 阻塞
- 死亡
Thread:多线程的类
- currentThread()
- getName() ,setName()
- sleep()
实现多线程的方式
1. 继承Thread,重写run
2. 实现Runnable,重写run
实现线程安全的三种方式
线程的执行是靠cpu分配时间片
存在一票多卖:多个线程同时访问一个数据,同一个数据被访问多次,存在线程安全问题
线程安全问题是怎样发生:线程要执行的代码还没有全部执行完,另一个线程有开是执行
怎样来解决这个线程安全问题:保证线程要执行的代码全部要执行完毕
synchronized (参数:引用类型,所有的线程对象都能共享的(static修饰,字节码对象) )
-
同步代码块:将同步代码快作为一个整体
继承Thread,重写run
public class Tickets extends Thread{ private static int count = 1; public Tickets() { } public Tickets(String name) { super(name); } @Override public void run() { for (int i = 0; i < 30; i++) { synchronized (this.getClass()) { if(count <= 30) { // 获取当前线程的名 String name = Thread.currentThread().getName(); System.out.println(name + "窗口:卖出第" + count + "张票"); count++; try { Thread.sleep(100); } catch (InterruptedException e) { throw new RuntimeException(e); } } } } } }
// 测试类 public class TicketsTest { public static void main(String[] args) { Tickets t1 = new Tickets("花泽"); Tickets t2 = new Tickets("龙泽"); Tickets t3 = new Tickets("波多野蘋蘋"); t3.setPriority(Thread.MAX_PRIORITY); t1.start(); t2.start(); t3.start(); } }
实现Runnable,重写run
public class Tickets implements Runnable { private int count = 1; // 可以是实例变量,也可以是类变量 private ReentrantLock lock = new ReentrantLock(true); // 使用同步代码块来处理线程不安全的问题 public void run() { for (int i = 0; i < 30; i++) { synchronized (this.getClass()) { // this:当前对象 if (count <= 30) { String name = Thread.currentThread().getName(); // 获取当前线程的名字 System.out.println(name + "窗口:卖出第" + count + "张票"); count++; } try { Thread.sleep(100); } catch (InterruptedException e) { throw new RuntimeException(e); } } } } }
// 测试类 public class TicketsTest { public static void main(String[] args) { // 1、创建Runnable对象 Tickets tickets = new Tickets(); // 2、创建线程 Thread t1 = new Thread(tickets, "蘋蘋1号"); Thread t2 = new Thread(tickets, "蘋蘋2号"); Thread t3 = new Thread(tickets, "蘋蘋3号"); // 3、启动线程 t1.start(); t2.start(); t3.start(); } }
-
同步方法:用synchronized 修饰方法
继承Thread,重写run
public class Tickets2 extends Thread{ private static int count = 1; public Tickets2() { } public Tickets2(String name) { super(name); } // 设计一个买票的方法 public static synchronized void sale() { // 这个就是同步方法,同步实例方法的锁默认是this,同步类方法的锁是当前类的字节码对象 if (count <= 30) { // 获取当前线程的名 String name = Thread.currentThread().getName(); System.out.println(name + "窗口:卖出第" + count + "张票"); count++; } } @Override public void run() { for (int i = 0; i < 30; i++) { sale(); try { Thread.sleep(100); } catch (InterruptedException e) { throw new RuntimeException(e); } } } }
public class Tickets2Test { public static void main(String[] args) { Tickets2 t1 = new Tickets2("花泽"); Tickets2 t2 = new Tickets2("龙泽"); Tickets2 t3 = new Tickets2("波多野蘋蘋"); t3.setPriority(Thread.MAX_PRIORITY); t1.start(); t2.start(); t3.start(); } }
实现Runnable,重写run
public class Tickets implements Runnable { private int count = 1; // 可以是实例变量,也可以是类变量 private ReentrantLock lock = new ReentrantLock(true); // 使用同步方法 public synchronized void sale() { if (count <= 30) { String name = Thread.currentThread().getName(); // 获取当前线程的名字 System.out.println(name + "窗口:卖出第" + count + "张票"); count++; } } @Override public void run() { for (int i = 0; i < 30; i++) { sale(); try { Thread.sleep(100); } catch (InterruptedException e) { throw new RuntimeException(e); } } } }
// 测试类 public class TicketsTest { public static void main(String[] args) { // 1、创建Runnable对象 Tickets tickets = new Tickets(); // 2、创建线程 Thread t1 = new Thread(tickets, "蘋蘋1号"); Thread t2 = new Thread(tickets, "蘋蘋2号"); Thread t3 = new Thread(tickets, "蘋蘋3号"); // 3、启动线程 t1.start(); t2.start(); t3.start(); } }
-
同步锁:ReentrantLock,lock():上锁,unlock():解锁
继承Thread,重写run
public class Tickets3 extends Thread{ // 创建同步锁 private static ReentrantLock lock = new ReentrantLock(true); // 不带公平机制 private static int count = 1; public Tickets3() { } public Tickets3(String name) { super(name); } @Override public void run() { // 使用同步锁 for (int i = 0; i < 30; i++) { // 上锁 lock.lock(); try { if (count <= 30) { // 获取当前线程的名 String name = Thread.currentThread().getName(); System.out.println(name + "窗口:卖出第" + count + "张票"); count++; try { Thread.sleep(100); } catch (InterruptedException e) { throw new RuntimeException(e); } } }finally { // 释放锁 lock.unlock(); } } } }
public class Tickets3Test { public static void main(String[] args) { Tickets3 t1 = new Tickets3("花泽"); Tickets3 t2 = new Tickets3("龙泽"); Tickets3 t3 = new Tickets3("波多野蘋蘋"); t3.setPriority(Thread.MAX_PRIORITY); t1.start(); t2.start(); t3.start(); } }
实现Runnable,重写run
public class Tickets implements Runnable { private int count = 1; // 可以是实例变量,也可以是类变量 private ReentrantLock lock = new ReentrantLock(true); // 使用同步锁 @Override public void run() { for (int i = 0; i < 30; i++) { // 上锁 lock.lock(); try { if (count <= 30) { String name = Thread.currentThread().getName(); // 获取当前线程的名字 System.out.println(name + "窗口:卖出第" + count + "张票"); count++; } try { Thread.sleep(100); } catch (InterruptedException e) { throw new RuntimeException(e); } }finally { // 解锁 lock.unlock(); } } } }
// 测试类 public class TicketsTest { public static void main(String[] args) { // 1、创建Runnable对象 Tickets tickets = new Tickets(); // 2、创建线程 Thread t1 = new Thread(tickets, "蘋蘋1号"); Thread t2 = new Thread(tickets, "蘋蘋2号"); Thread t3 = new Thread(tickets, "蘋蘋3号"); // 3、启动线程 t1.start(); t2.start(); t3.start(); } }
Timer:定时器(也可作为守护线程)
定时器:在指定时间做指定事情,比如:闹钟
在开发定时器的作用:1、定时发邮件 2、定时备份 3、定时写日志
就是学习一个类:Timer:定时器类,做定时任务的
TimerTask:定时任务,另外一个线程
// 定时任务
import java.util.TimerTask;
/**
* 写一个定时任务
*/
public class SayHi extends TimerTask {
@Override
public void run() {
System.out.println("hello boys and girls......");
}
}
// 测试类
import java.util.Calendar;
import java.util.Date;
import java.util.Timer;
public class TimerDemo {
public static void main(String[] args) {
// 创建一个定时器
Timer timer = new Timer(); // 创建了一个线程
// 调用其他线程:schedule()
SayHi sayHi = new SayHi();
// timer.schedule(sayHi,2000); // 2秒后执行定时任务,一次性任务
// timer.schedule(sayHi,2000,3000); // 周期性的任务
Calendar cal = Calendar.getInstance();
cal.add(Calendar.SECOND, -10);
Date date = cal.getTime();
// timer.schedule(sayHi,date,3000);
timer.scheduleAtFixedRate(sayHi,date,3000);
}
}
标签:Tickets,定时器,Thread,start,线程,&&,new,public
From: https://www.cnblogs.com/JunYuanStudy/p/17933550.html