Java_多线程_成员变量与局部变量

线程会共享进程范围内的资源,例如内存句柄和文件句柄,但每个线程都有各自的程序计数器、栈及局部变量等。线程还提供了一种直观的分解模式来充分利用多处理器系统中的硬件并行性,而在同一个程序中的多个线程还可以被同时调度到多个CPU上运行。线程也被称为轻量级进程。在大多数现代操作系统中,都是以线程为基本的调度单位,而不是进程。同一个进程中的所有线程都将共享进程的内存地址空间,因此这些线程都能访问相同的成员变量并在同一个堆上分配对象。

成员变量:

package deep;

public class MemberVariableThread implements Runnable {

    private int i;// 成员变量被初始化为0

    @Override
    public void run() {
        while (true) {
            System.out.println(Thread.currentThread().getName() + ":" + i++);
            try {
                Thread.sleep(100);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            if (50 == i) {
                break;
            }
        }
    }
}
package deep;

public class Test {
    public static void main(String[] args) {
        MemberVariableThread memberVariableThread = new MemberVariableThread();
        Thread thread1 = new Thread(memberVariableThread);
        Thread thread2 = new Thread(memberVariableThread);
        thread1.start();
        thread2.start();
    }
}

运行结果:

Thread-0:0

Thread-1:0

Thread-0:1

Thread-1:2

Thread-0:3

Thread-1:4

Thread-0:5

Thread-1:5

Thread-1:6

Thread-0:6

Thread-0:7

Thread-1:8

Thread-0:9

Thread-1:10

Thread-0:11

Thread-1:12

Thread-0:13

Thread-1:14

Thread-0:15

Thread-1:16

Thread-0:17

Thread-1:18

Thread-0:19

Thread-1:20

Thread-0:21

Thread-1:22

Thread-0:23

Thread-1:24

Thread-0:25

Thread-1:26

Thread-0:27

Thread-1:28

Thread-0:29

Thread-1:30

Thread-0:31

Thread-1:32

Thread-0:33

Thread-1:34

Thread-0:35

Thread-1:36

Thread-0:37

Thread-1:38

Thread-0:39

Thread-1:40

Thread-0:41

Thread-1:42

Thread-0:43

Thread-1:44

Thread-0:45

Thread-1:46

Thread-0:47

Thread-1:48

Thread-0:49

在此例中,i是成员变量,两个线程都由同一个类构造,所以共享了同一个i,同时也可以观察到此类不是线程安全的,因为i++不是一个原子性操作。此例仅是为了说明成员变量会被多个线程共享,所以必须采取其他的机制保证线程安全性。

局部变量:

package deep;

public class LocalVariableThread implements Runnable {

    @Override
    public void run() {
        int i = 0; // 每一个线程都会拥有自己的一份局部变量的拷贝,线程之间互不影响,所以会打印100个数字,0到49每个数字都是两遍
        while (true) {
            System.out.println(Thread.currentThread().getName() + ":" + i++);
            if (50 == i) {
                break;
            }
        }

    }

}
package deep;

public class Test {
    public static void main(String[] args) {
        LocalVariableThread localVariableThread = new LocalVariableThread();
        Thread thread1 = new Thread(localVariableThread);
        Thread thread2 = new Thread(localVariableThread);
        thread1.start();
        thread2.start();
    }
}

运行结果:

Thread-0:0

Thread-1:0

Thread-0:1

Thread-1:1

Thread-0:2

Thread-1:2

Thread-0:3

Thread-1:3

Thread-0:4

Thread-1:4

Thread-0:5

Thread-1:5

Thread-0:6

Thread-1:6

Thread-0:7

Thread-1:7

Thread-0:8

Thread-0:9

Thread-1:8

Thread-0:10

Thread-1:9

Thread-0:11

Thread-1:10

Thread-1:11

Thread-1:12

Thread-1:13

Thread-0:12

Thread-1:14

Thread-0:13

Thread-1:15

Thread-0:14

Thread-1:16

Thread-0:15

Thread-1:17

Thread-0:16

Thread-1:18

Thread-0:17

Thread-1:19

Thread-0:18

Thread-1:20

Thread-0:19

Thread-1:21

Thread-0:20

Thread-1:22

Thread-1:23

Thread-1:24

Thread-1:25

Thread-1:26

Thread-1:27

Thread-1:28

Thread-1:29

Thread-1:30

Thread-1:31

Thread-1:32

Thread-1:33

Thread-0:21

Thread-1:34

Thread-1:35

Thread-0:22

Thread-1:36

Thread-0:23

Thread-0:24

Thread-1:37

Thread-0:25

Thread-1:38

Thread-0:26

Thread-1:39

Thread-0:27

Thread-1:40

Thread-0:28

Thread-1:41

Thread-0:29

Thread-1:42

Thread-0:30

Thread-1:43

Thread-0:31

Thread-1:44

Thread-0:32

Thread-1:45

Thread-0:33

Thread-1:46

Thread-0:34

Thread-1:47

Thread-0:35

Thread-1:48

Thread-0:36

Thread-1:49

Thread-0:37

Thread-0:38

Thread-0:39

Thread-0:40

Thread-0:41

Thread-0:42

Thread-0:43

Thread-0:44

Thread-0:45

Thread-0:46

Thread-0:47

Thread-0:48

Thread-0:49

如注释中所述,由于局部变量对于每一个线程来说都有自己的拷贝,所以各个线程之间不再共享同一个变量,输出结果为100个数字,实际上是两组,每组都是0到49的50个数字,并且两组数字之间随意地穿插在一起。

总结:

  • 如果一个变量是成员变量,那么多个线程对同一个对象的成员变量进行操作时,它们对该成员变量是彼此影响的,也就是说一个线程对成员变量的改变会影响到另一个线程。
  • 如果一个变量是局部变量,那么每个线程都会有一个该局部变量的拷贝(即便是同一个对象中的方法的局部变量,也会对每一个线程有一个拷贝),一个线程对该局部变量的改变不会影响到其他线程。
时间: 2024-10-30 02:24:58

Java_多线程_成员变量与局部变量的相关文章

java类与对象_成员变量和局部变量区别

成员变量和局部变量:1.成员变量:再类中定义,用来描述对象将要有什么.2.局部变量:在类的方法中定义,在方法中临时保存数据.区别:1.作用域不同:  局部:仅限于定义它的方法  成员:整个类中都是可见的2.初始值不同的  局部:Java不会给局部变量赋予初始值  成员:Java给成员变量赋予初始值,03在同一个方法中不允许有同名的局部变量:不同的方法中可以有同名的局部变量4.两类变量同名时,局部变量有更高的优先级(就近原则)

【转】Java 多线程(四) 多线程访问成员变量与局部变量

原文网址:http://www.cnblogs.com/mengdd/archive/2013/02/16/2913659.html 先看一个程序例子: public class HelloThreadTest { public static void main(String[] args) { HelloThread r = new HelloThread(); Thread t1 = new Thread(r); Thread t2 = new Thread(r); t1.start();

面向对象_成员变量和局部变量的区别

作用范围: 局部变量作用于函数中或者语句中(定义在函数或语句中(比如for语句),必须初始化) 成员变量作用于整个类中(定义在类中,有默认初始化值,可以定义显示初始化值) 在内存中的位置: 成员变量在堆内存中.因为对象的存在,才在内存中存在. 局部变量在栈内存中. 如果成员变量没有定义显示初始化,那么系统默认会初始化(在堆内存中的变量都会有默认初始化值)byte 0short 0int 0long 0Ldouble 0.0Dfloat 0.0fboolean false引用数据类型默认初始化值都

Java 多线程(四) 多线程访问成员变量与局部变量

先看一个程序例子: public class HelloThreadTest { public static void main(String[] args) { HelloThread r = new HelloThread(); Thread t1 = new Thread(r); Thread t2 = new Thread(r); t1.start(); t2.start(); } } class HelloThread implements Runnable { int i; @Ove

多线程访问成员变量与局部变量

ThreadLocal是JDK引入的一种机制,它用于解决线程间共享变量,使用ThreadLocal声明的变量,即使在线程中属于全局变量,针对每个线程来讲,这个变量也是独立的. 它通过为每个线程提供一个独立的变量副本解决了变量并发访问的冲突问题.在很多情况下,ThreadLocal比直接使用synchronized同步机制解决线程安全问题更简单,更方便,且结果程序拥有更高的并发性. 详解:http://blog.csdn.net/gaogaoshan/article/details/9312703

java 线程---成员变量与局部变量

关于成员变量与局部变量: 如果一个变量是成员变量,那么多个线程对同一个对象的成员变量进行操作时,他们对该成员变量是彼此影响的(也就是说一个线程对成员变量的改变会影响到另一个线程) . 如果一个变量是局部变量,那么每个线程都会有一个该局部变量的拷贝,一个线程对该局部变量的改变不会影响到其他的线程. 实例: Servlet容器为了响应多个用户同时访问一个Servlet的HTTP请求,通常会为每个请求分配一个工作线程,这些工作线程并发执行同一个Servlet(即Servlet是单实例的)的servic

成员变量和局部变量

成员变量和局部变量 1.变量声明的位置决定变量作用域 2.变量作用域确定可在程序中按变量名访问该变量的区域 3.成员变量:定义在类中的变量(类或其他类中可以调用) 4.局部变量:定义在方法中的变量(方法) 5.区别:a.作用域不同 局部变量的作用域仅限于定义它的方法 成员变量的作用域在整个类内部都是可见的 b.初始值不同 Java会给成员变量一个初始值 Java不会给局部变量赋予初始值 6.在同个方法中,不允许有同名局部变量 ,在不同方法中,可以有同名的局部变量, 在同个类中,成员变量和局部变量

成员变量与局部变量

  初始值 作用域 优先级 成员变量 java会给成员变量一个初始值 受访问控制修饰符影响作用域不同 成员变量与局部变量同名时,优先使用局部变量 局部变量 java不会给局部变量赋初始值 方法内,代码块作用域 初始值比较: 1 public class Var { 2 private static int var1;// 成员变量 3 4 public void method() { 5 int var2;// 局部变量 6 System.out.println(var1);// 编译通过,成员

Java基础——成员变量、局部变量和静态变量的区别

之前在刚开始学习Java的时候,就谈了谈Java基础中的变量,虽然知道这货以后会经常用到,但没想到了基本语法这里,竟然有冒出来了成员变量.局部变量和静态变量.变来变去太容易让人搞晕了,挑拣出来梳理一下喽! 要想区分这哥仨,首先,我们得知道它们分别是什么.先从成员变量下刀. 成员变量 我们来研究一个事物: 属性:外在特征:例如人的身高,体重 行为:能够做什么:例如人有说话,打球等行为. 而在Java语言中,最基本的单位是类,类就是用来体现事物的. 用类class来描述事物也是如此: 属性:对应类中