java的多线程是理解springboot的一个重要概念,它的理念就是让进程并发进行,防止任务阻塞整个程序。
- 多线程的创建方法有三种
-
- 继承Thread类
-
- 实现 Runnable接口
-
- 实现Callable接口
public class MyTread extends Thread{
@Override
public void run(){
//代码块
}
}
public class Main{
public static void main(String[] ards){
Thread t =new MyThread();
t.start();
}
//这里可以写主线程
}
- 第一个开启方式 继承 Thread 类
- 这就启动了两个线程,这里得注意,主线程得放到start后面,因为放在前面两个线程没有同时打开,会先执行完主线程再开启子线程并执行代码。
- 优点:简单
- 缺点:没法继承方法(无法扩展)
class MyRunnable implements Runnable {
@Override
public void run() {
System.out.println("线程2:实现 Runnable 运行中");
} }
public class Test {
public static void main(String[] args) {
Thread t = new Thread(new MyRunnable());
t.start();
}
}
- 第二个开启方法 实现 Runnable 接口(重写run方法)
- 优点: 不占用继承名额
- 缺点: 没有返回值 不能直接抛出异常 只能使用try-catch
import java.util.concurrent.FutureTask;
// 1. 实现 Callable
class MyCallable implements Callable<String> {
// 2. 重写 call(有返回值)
@Override
public String call() {
return "线程3:Callable 运行完毕,返回结果";
}
}
public class Test {
public static void main(String[] args) throws Exception {
// 3. 包装成 FutureTask
FutureTask<String> task = new FutureTask<>(new MyCallable());
// 4. 启动
new Thread(task).start();
// 5. 获取返回值
System.out.println(task.get());
}
}
- 优点: 有返回值 可直接抛异常
- 缺点: 复杂 获取结果阻塞主线程
- String泛型是返回值类型
现在有问题了每次多个线程同时访问同一个数据
如果在同时进行判断,则会影响线程安全
解决方案: 加锁
加锁:每次只允许一个线程加锁,加锁后才进行访问,访问完后自动解锁,其他线程才能再次加锁进来