java线程安全问题如何解决

java线程安全问题如何解决

  • 重写 Runnable接口种的run方法
package cn.tread;

public class runnable implements Runnable {
    private int ticket =100;
    @Override
    public void run() {
        while (true){
            if (ticket>0){
                System.out.println(Thread.currentThread().getName()+"正在买"+ticket+"张票");
                ticket--;
            }
        }
    }
  • 创建一个刚才写的实例对象 调用
    New 一个Thread对象吧刚才的实例对象放进去用start方法运行
package cn.tread;

public class demo {
    public static void main(String[] args) {
        runnable demo1=  new runnable();
//        Thread用来创建线程//        Thread用来创建线程 构造方法种传递runnable实现类对象
        Thread to1 = new Thread(demo1);
        Thread to2 = new Thread(demo1);
        Thread to3 = new Thread(demo1);
        to1.start();
        to2.start();
        to3.start();

    }
}

安全问题产生的原因

本案例开启三个线程,三个线程抢夺执行权,他执行到if语句就会失去cpu执行权,速度太快都在执行第一个的时候同时打印

解决方法

  • 同步代码块
package cn.线程;

public class runnable implements Runnable {
    private int ticket =100;
    Object obj = new Object();
    @Override
    public void run() {
        while (true){
			//同步代码块 synchronized 
            //可以使用任意对象Synchronized是Java中解决并发问题的一种最常用最简单的方法 ,他可以确保线程互斥的访问同步代码
          synchronized (obj){
              if (ticket>0){
                  try {
                      Thread.sleep(10);
                  } catch (InterruptedException e) {
                      e.printStackTrace();
                  }
                  System.out.println(Thread.currentThread().getName()+"正在买"+ticket+"张票");
                  ticket--;
              }else {
                    break;
              }
          }
        }
    }
  • 同步方法
    定义格式
    修饰符 synchronized 返回值类型 方法名(参数列表){
    共享数据的代码 / 有问题代码可能出现重复数据
    }
package cn.线程;

public class runnable implements Runnable {
    private int ticket =100;
    Object obj = new Object();
    @Override
    public void run() {
        while (true){
//        同步代码块
            //可以使用任意对象
            payket();
        }
    }
    public synchronized void payket(){
            if (ticket>0){
                try {
                    Thread.sleep(10);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                System.out.println(Thread.currentThread().getName()+"正在买"+ticket+"张票");
                ticket--;
            }
    }
  • 锁机制
  • public class ReentrantLock implements Lock, java.io.Serializable
  • 如果使用Lock 需要调用Lock子类 renntrantlock
  • Lock 更加先进以及好用
    lock 获取锁
    unlock 释放锁

你可能感兴趣的:(java)