A股上市公司传智教育(股票代码 003032)旗下技术交流社区北京昌平校区

 找回密码
 加入黑马

QQ登录

只需一步,快速开始

© 高鑫 中级黑马   /  2012-5-5 15:38  /  2599 人查看  /  6 人回复  /   0 人收藏 转载请遵从CC协议 禁止商业使用本文

请问,为什么主函数存在于栈内存中,而对象中的函数在方法区?

评分

参与人数 1技术分 +1 收起 理由
贠(yun)靖 + 1

查看全部评分

6 个回复

正序浏览
本帖最后由 廖理 于 2012-5-5 19:16 编辑

类的方法是类的对象所共有的,所以类的方法在对象创建时被加载进了内存中的方法区,这些方法代码块就可以被所有创建的此类对象共有,共同使用,而不用每个对象中都保存一份代码块,节省了内存空间。当类的对象调用的到该方法时,Jvm会自动在方法中找到对应的方法,然后再将该方法加载到栈中,执行该行法。
方法在调用时都要被加载如Static才能运行,Main方法是程序的入口,由JVm直接调用,而且他是一个静态方法,但主函数比较特殊,主方法会在构造器之前,static变量初始化之后调用,这是由于Java的惰性初始化,在main方法被调用之前无法知道是否存在主类的实例。所以他是先于对象而存在的,所以调用他之后,才会创建对象, ,当对象调用方法时,Jvm就自动将对应方法加载到Stack中运行,此方法完成后自动从Stack内存中消失,但是方法区方法代码依然存在。main方法完成后也会从Stack中消失,即整个程序结束了。
回复 使用道具 举报
   java 虚拟机提供了程序运行时环境,其中,运行时环境中最重要的一个资源是运行时数据区。运行时数据区是操作系统为java虚拟进程分配的内存区域,java虚拟机操作着这块区域。
    运行时数据区又划分为几个子区:
     1.堆区:存放对象。
     2.方法区:存放类的类型信息(静态变量和方法信息)
     3.java栈区。
以一个小程序为例:
public class Amain
{
     public static void main(String[] arr)
     {
           Sa s = new Sa("ren");
           s.printName();
      }
}
class Sa
{
     String name;
      Sa(String name)
      {
            this.name = name;
      }
      void printName()
      {
            System.out.println(name);
      }
}
Sal类的类信息包括Sa类中的printName()还有Amain类的信息(包括main方法)方法在方法区内。
栈内存中存放着执行main()方法的主线程的方法掉用栈。
此程java虚拟机的运行过程为:首先在程序加载的时候找classpath文件中找到Amain.class类把它中的信息加载到方法区内,然后java虚拟机定位Amain中的main方法的字节码开始执行它的命令,加载Sa类信息到方法区,创建对象,并定位printName的字节码,执行printName()命令。



回复 使用道具 举报
小弟是这样理解的
栈区( stack ) 由jvm自动分配释放 ,存放函数的参数值,局部变量的值,栈内存分配运算内置于处理器的指令集中,效率很高,但是分配的内存容量有限(网上搜的)。
方法区 存放二进制方法(网上)
因为主函数是唯一的,又被jvm所调用,所以放到了栈区。
而对象中函数可能有许多,又不需要高效,所以放到了方法区。
回复 使用道具 举报
我觉得是操作系统分配的吧, 呵呵,还有根据堆栈的内存方式,堆是先进先出,栈是先进后出。 仅供参考。。
回复 使用道具 举报
规则就是这样的吧
回复 使用道具 举报
呵呵   我也想知道  
回复 使用道具 举报
您需要登录后才可以回帖 登录 | 加入黑马