zoukankan      html  css  js  c++  java
  • 【java基础领域】并发编程基础问题

    线程安全:当多个线程访问某一个类(对象或方法时),这个类始终都能实现出正确的行为。那么这个类就是线程安全的。

    package com.hbsi.thread;
    
    /***
     * 并发编程基础
     * @author jia
     *
     */
    public class MyThread extends Thread{
    	
    	int sum = 5;
    	
    	@Override
    	public void run(){
    		sum--;
    		System.out.println(Thread.currentThread().getName()+" sum的值是:"+sum);
    		
    	}
    
    	public static void main(String[] args) {
    		
    		Thread thread = new MyThread();
    		Thread t1 = new Thread(thread,"t1");
    		Thread t2 = new Thread(thread,"t2");
    		Thread t3 = new Thread(thread,"t3");
    		Thread t4 = new Thread(thread,"t4");
    		Thread t5 = new Thread(thread,"t5");
    		
    		t1.start();
    		t2.start();
    		t3.start();
    		t4.start();
    		t5.start();
    	}
    	
    	
    }
    

    以上代码执行的结果是:

    t2 sum的值是:3
    t3 sum的值是:1
    t4 sum的值是:2
    t1 sum的值是:3
    t5 sum的值是:0
    可以看到,线程的执行并不会按照我们所规定的程序顺序流程执行。因此sum的值不是从5-0之间变化的。由此,就出现了当多个线程对同一个对象进行数据修改时,就会出现数据不一致的现象。

    出现此种情况,通常我们使用synchronized加锁控制。

    代码修改如下,

    package com.hbsi.thread;
    
    /***
     * 并发编程基础
     * @author jia
     *
     */
    public class MyThread extends Thread{
    	
    	int sum = 5;
    	
    	@Override
    	public synchronized void run(){
    		sum--;
    		System.out.println(Thread.currentThread().getName()+" sum的值是:"+sum);
    		
    	}
    
    	public static void main(String[] args) {
    		
    		Thread thread = new MyThread();
    		Thread t1 = new Thread(thread,"t1");
    		Thread t2 = new Thread(thread,"t2");
    		Thread t3 = new Thread(thread,"t3");
    		Thread t4 = new Thread(thread,"t4");
    		Thread t5 = new Thread(thread,"t5");
    		
    		t1.start();
    		t2.start();
    		t3.start();
    		t4.start();
    		t5.start();
    	}
    	
    	
    }
    

    只是在run方法上进行了加锁控制。

    执行结果:

    t1 sum的值是:4
    t5 sum的值是:3
    t4 sum的值是:2
    t3 sum的值是:1
    t2 sum的值是:0
    现在可以看到,执行的结果是递减的,但是线程并不是按照之前代码顺序结构进行执行的。

    这一块,我们可以理解一下,当多个线程访问MyThread的run方法时,以排队的方式进行处理(这里的排队是按照cpu分配的顺序而定的,相当于抢占cpu的执行权),一个线程想要执行synchroized修饰的方法里的代码。首先应该先获取锁。如果拿到锁就执行synchroized代码里的内容,拿不到锁这个线程就不断的尝试这把锁,直到拿到为止。多个线程获取同一把锁,就会出锁竞争的问题。

  • 相关阅读:
    庖丁解牛识控件
    打开地图文件和shape文件代码加载Mxd文档
    IMapControl3 Interface(1) Properties属性
    避免事件响应传递依赖
    提示:ArcGIS version not specified. You must call RuntimeManager.Bind before creating any ArcGIS components.错误
    我的联想笔记本电脑为啥字母键变成数字键怎么切换过来
    C#读取word文件
    TensorFlow笔记(基础篇):加载数据之预加载数据与填充数据
    7.1 TensorFlow笔记(基础篇):加载数据之预加载数据与填充数据
    7.2 TensorFlow笔记(基础篇): 生成TFRecords文件
  • 原文地址:https://www.cnblogs.com/qxlxi/p/12860839.html
Copyright © 2011-2022 走看看