注册 登录
编程论坛 JAVA论坛

以下程序执行后,为什么t2调用i的值得到3呢?哪位高手能详解以下吗?感激不尽!!

notbad301 发布于 2018-02-26 21:56, 1745 次点击
public class Transfer {
    static int i=47;
     public void call() {
         for (i=0;i<3;i++) {
             System.out.print(i+" ");
             if(i==2) {
                 System.out.println("\n");
             }
         }
         
         
     }
     public Transfer() {
     }
     
    public static void main(String[] args) {
        Transfer t1=new Transfer();
        Transfer t2=new Transfer();
        System.out.println(t1.i);
        t1.call();
        System.out.println(t2.i);
        t2.call();

    }

}
6 回复
#2
疯狂的小a2018-02-26 22:27
package com.xiaoa.demo;


/**
 * @author niyite
 *
 */
/*
 * 分析输出结果
47:main方法是程序入口,执行System.out.println(t1.i);,t1对象的属性i的默认值是static int i = 47;,所以输出47
0 :t1调用call()方法,i的值被for声明成了0,for (i = 0; i < 3; i++) ,输出0,System.out.println(i + " ");
1 :i++变成了1,此时的i就是1
2 :i++变成了2,此时的i就是2
    :i等于2就会执行换行System.out.println("\n");i++变成了3,此时i就是3
   
3 :创建t2对象后,t2的i属性就是3,所以这里输出3
0 :t2调用call()方法,i的值被for声明成了0,for (i = 0; i < 3; i++) ,输出0,System.out.println(i + " ");
1 :i++变成了1,此时的i就是1
2 :i++变成了2,此时的i就是2

注意static int i = 47;是在成员位置,创建对象就是,i就是对象的属性
 */
public class Transfer {
    static int i = 47;
    public void call() {
        for (i = 0; i < 3; i++) {
            System.out.println(i + " ");
            if (i == 2) {
                System.out.println("\n");
            }
        }
    }
    public Transfer() {
    }
    public static void main(String[] args) {
        Transfer t1 = new Transfer();
        Transfer t2 = new Transfer();
        System.out.println(t1.i);
        t1.call();
        System.out.println(t2.i);
        t2.call();
    }
}
#3
notbad3012018-02-26 22:49

如果去掉static后,t2调用i的值就变成47了,那么这个static起到的作用是什么呢?

public class Transfer {
    int i=47;
     public void call() {
         for (i=0;i<3;i++) {
             System.out.print(i+" ");
             if(i==2) {
                 System.out.println("\n");
             }
         }
         
         
     }
     public Transfer() {
     }
     
    public static void main(String[] args) {
        Transfer t1=new Transfer();
        Transfer t2=new Transfer();
        System.out.println(t1.i);
        t1.call();
        System.out.println(t2.i);
        t2.call();

    }

}
#4
疯狂的小a2018-02-26 22:56
回复 3楼 notbad301
static修饰的成员变量,可以理解为只能赋值一次,就是第一次创建对象时,创建了一个i,然后赋值一次。在内存中是放在了常量池中。后面再创建对象,i的值就是从常量池直接取值。如果不用static修饰就是每次创建对象,都创建一个新的i。这个,新手比较难理解,建议看看书
#5
notbad3012018-02-26 23:20
这样变了一下,将输出t2时的命令,改为了:System.out.println(t2.i=80);

整个命令为:


public class Transfer {
    static int i=47;
     public void call() {
         for (i=0;i<3;i++) {
             System.out.print(i+" ");
             if(i==2) {
                 System.out.println("\n");
             }
         }
         
         
     }
     public Transfer() {}
     
    public static void main(String[] args) {
        Transfer t1=new Transfer();
        Transfer t2=new Transfer();
        System.out.println(t1.i);
                t1.call();
                System.out.println(t2.i=80);
                t2.call();

            }

}

得到t2就不是3,而是80了。哪怕是执行t1.call()最后一步将3赋值给i,只要有static存在,到t2调用i的时候,还是可以改变i的值赋给t2(即80)。 这个static是否可以理解为存在时允许对象改变成员变量的值?如没有static,即便在建立某个对象时改变了成员变量的值,在建立下一个对象时,还是能够使用这个成员变量的初始值。
#6
疯狂的小a2018-02-26 23:34
回复 5楼 notbad301
不好意思,理解错了。这个位置赋值80就是在输出的时候改变了一下t2的i的值。
static修饰的成员变量,会放在常量池中,常量池中的i可以改变值。但是下次创建对象,还是用这个i。如果不用static修饰就是放在栈内存中,每次创建对象,都初始化一个i,i的值就是你在成员位置给的值。
#7
notbad3012018-02-26 23:48
谢谢您的详细解答!
1