黑马程序员技术交流社区

标题: 成员变量与局部变量--深入思考 [打印本页]

作者: SpiderManZZH    时间: 2014-11-21 11:41
标题: 成员变量与局部变量--深入思考
根据上一个帖子,http://bbs.itheima.com/forum.php?mod=viewthread&tid=153546&page=1#pid1083772
因为看到有的朋友回复,现把调用代码加上,并且通过查看各位的回复也让我有更多的疑问,请各位朋友一起探讨

//对Car这类事物进行描述
class Car
{
             //成员变量
             String color = "red";
             int num = 4;
            //成员方法
            void show()
          {
                 //临时变量
                int num = 10;
                //输出临时变量的值
               System. out.println("color = " +color +"...num = " +num);
          }
}
class CarDemo
{
         public static void main(String[] args)
         {
            //通过new关键字,建立对象
            //c就是一个类类型的引用变量,指向了该类的对象
            Car c = new Car();
            //对对象的属性进行修改
            c. color = "black" ;
            //输出成员变量的默认值
            System. out.println(c.num );
            //通过对象.成员的形式来使用对象的功能
            c.show();
         }  
}
打印结果:


如上所诉,通过实例化对象调用show()方法,打印的num是局部变量的值等于10,如果要打印成员变量代码可改为this.num
问题1:当成员变量和局部变量同名时,如果输出打印的是num不是this.num,为什么会默认是局部变量的值,而不是成员变量的值?
问题2:从内存中地址来分析,可知道当实例化对象后, 成员变量num存在于堆内存中,show()方法也是在堆内存中,当调用show()方法时,局部变量num是存在于栈内存中,这是可以明确的,但看到有个朋友说是标签相同时,调用show()方法,局部变量的值会覆盖成员变量的值,这就已经回答了第一个问题,
我想请问,两个变量的内存地址不一样,为什么也可以覆盖?

作者: Crazy_Eat_Code    时间: 2014-11-21 12:18
哥们 你有没有想过 调用的同时也进行赋值操作 既然可以赋值为什么不能覆盖(欲知详细 请再看毕老师 05 天 065 视频 05天)
作者: 郑飞    时间: 2014-11-21 12:28
我觉得覆盖只是说调用上的覆盖 实际东西还是各是各的 show()和this.num是平行的 都是局部成员 而show()中的num是show()身上的东西 所以这些调用规则还是非常遵循常理的 记忆上不存在问题 如果要深入就要多做扩展了
楼主可以上网看些内存分配的资料 比如实例过程 方法调用等等 我也看过 但是还不全面 理解不透彻 所以不好说 对于程序的优化 内存的使用效率等等 还是很有帮助的 昨天自己写了个工具类 发现一个变量的定义位置 直接导致运行效率提升50%
作者: SpiderManZZH    时间: 2014-11-21 13:03
郑飞 发表于 2014-11-21 12:28
我觉得覆盖只是说调用上的覆盖 实际东西还是各是各的 show()和this.num是平行的 都是局部成员 而show()中的 ...

:handshake听你这样一说,赶脚还有好多知识不懂啊
作者: cs8630323    时间: 2014-11-21 13:58
感觉是在走歪路,java不必太纠结底层的,没那个精力,也不是java的强项,这样纠结半天也只是得到个模棱两可的答案,对实际编程能力提高很小,想了解底层有机会就去深入C/C++
作者: zhangyangLengen    时间: 2014-11-21 14:41
哥们:
,show()方法也是在堆内存中,不是吧?应该存在于方法区中的非静态方法区。当你调用方法进栈时,此时的函数的局部变量会在栈中初始化,当你需要调用num时,且没有加上任何引用,底层就会从栈中进行查找,看有没有num这个变量,如果有,就行。如果没有就到对应堆中进行查找特定的地址的num值
作者: SpiderManZZH    时间: 2014-11-22 10:22
cs8630323 发表于 2014-11-21 13:58
感觉是在走歪路,java不必太纠结底层的,没那个精力,也不是java的强项,这样纠结半天也只是得到个模棱两可 ...

你这样说也对,但我感觉要知其然还要知其所以然




欢迎光临 黑马程序员技术交流社区 (http://bbs.itheima.com/) 黑马程序员IT技术论坛 X3.2