• 同步代码块和同步方法案例实战


    什么是同步

    • 同步就是加锁,不让其它人访问
    • synchronized指的就是同步的意思

    什么情况下需要同步

    当多线程并发, 我们希望某一段代码执行的过程中CPU不要切换到其他线程工作. 这时就需要同步,否则会有线程安全问题。

    同步代码块

    • 使用synchronized关键字加上一个锁对象来定义一段代码, 这就叫同步代码块
    • 多个同步代码块如果使用相同的锁对象, 那么他们就是同步的
    • 使用同步锁时,应该尽是让锁的范围小点,才能提高性能

    同步代码块案例:

    package demo;
    
    public class Task implements Runnable{
        private int tickets = 100;
        public void run(){
            while(true){
                synchronized (this){
                    if(tickets <= 0){
                        System.out.println("不好意思,票卖完了");
                        break;
                    }else{
                        System.out.println(Thread.currentThread()+"恭喜你买到票,票号"+tickets);
                        tickets--;
                    }
                }
            }
        }
    }
    package demo;
    
    public class SynchronizedDemo {
        public static void main(String[] args) {
            Task task = new Task();
            Thread t1 = new Thread(task);
            Thread t2 = new Thread(task);
            Thread t3 = new Thread(task);
            t1.start();
            t2.start();
            t3.start();
        }
    }

    同步方法

    • 使用synchronized关键字修饰一个方法, 该方法中所有的代码都是同步的
    • 非静态同步方法的锁是:this
    • 静态同步方法的锁是:字节码对象(xx.class)

    案例:卖火车票

    • 需求,有ABCD4个窗口同时买票,只有100张票可买
    • 多线程会有安全问题熟记
        //火车站卖票【问题】
            /**
             * 湖南到广州火车票:今天13:00 ,100张
             * 火车站有4个窗口在同时卖票,要保证一张票只能被卖一次
             * 
             * 搞4个线程表示4个窗口
             * 
             * 通过加锁可以解决被多次卖同一张票的问题
             * 
             * 使用同步代码块
             */
            
            //创建卖票的任务
            TicketTask task = new TicketTask();
            
            //A窗口
            Thread t1 = new Thread(task);
            t1.setName("窗口A");
            //B窗口
            Thread t2 = new Thread(task);
            t2.setName("窗口B");
            //C窗口
            Thread t3 = new Thread(task);
            t3.setName("窗口C");
            //D窗口
            Thread t4 = new Thread(task);
            t4.setName("窗口D");
            
            //开启线程
            t1.start();
            t2.start();
            t3.start();
            t4.start();
    class TicketTask implements Runnable{
        //只有100张票
        int ticket = 100;
        @Override
        public synchronized void run() {
            //卖票
            while (true) {
                if (ticket <= 0) {
                    System.out.println("不好意思,票已经卖完了...");
                    break;
                } else {
                    System.out.println(Thread.currentThread() + "恭喜你卖到票,票号" + ticket);
                    ticket--;
                }
            }
        }
        
        /*@Override
        public void run() {
            // TODO Auto-generated method stub
            *//**
             * 同步代码换括号里参数可以传任意对象
             * this是一个锁对象
             * 不同的一把锁,卖相同的票总是还是存在
             *//*
            
            //卖票
            while (true) {
                synchronized (String.class) {// 同步:加锁
                    if (ticket <= 0) {
                        System.out.println("不好意思,票已经卖完了...");
                        break;
                    } else {
                        System.out.println(Thread.currentThread() + "恭喜你卖到票,票号" + ticket);
                        ticket--;
                    }
                }
            }
        }*/
        
        /*@Override
        public void run() {
            // TODO Auto-generated method stub
            *//**
             * 同步代码换括号里参数可以传任意对象
             *//*
            synchronized (this) {
                //卖票
                while(true){
                    if(ticket <= 0){
                        System.out.println("不好意思,票已经卖完了...");
                        break;
                    }else{
                        System.out.println(Thread.currentThread() + "恭喜你卖到票,票号" + ticket);
                        ticket --;
                    }
                }
            }
        }*/
    }
  • 相关阅读:
    EasyNVR流媒体平台录像中断日志报Hls:force fragment splite错误解决
    视频流媒体服务器稳定吗?出现播放中断问题怎么办?
    RTSP/RTMP/GB/T28181视频流媒体服务器可以集成iframe地址无法播放问题解决
    新版视频流媒体服务器首页界面版本号显示异常问题解决
    新版视频流媒体服务器EasyNVR偶现父DIV背景色暴露问题解决
    视频云管理平台EasyNVS报NullPointerException异常问题解决
    视频流媒体服务器在幼儿园移动监控APP中显示“数据任意备份风险”提示问题解决
    视频流媒体服务器EasyNVR支持幼儿园安防监控中日志报no protocal错误问题解决
    视频流媒体服务器在幼儿园移动监控APP中“组件导出风险”修复
    流媒体服务器EasyNVR接口的登录鉴权报"Unauthorized"错误解决
  • 原文地址:https://www.cnblogs.com/ivan5277/p/10159605.html
Copyright © 2020-2023  润新知