JAVA:

A a = new A();

为A对象创建了一个实例,但在内存中开辟了两块空间:一块空间在堆区,存放new A()这个对象;另一块空间在堆栈,也就是栈,存放a,a的值为new A()这个对象的内存地址。因为java在JVM中运行,所以a 描述的内存地址不一定是这个对象真实内存的地址。

Object o; // 这是声明一个引用,它的类型是Object,他的值为null,还没有指向任何对象,该引用放在内存的栈区域中。

o = new Object(); //new Object()句,实例化了一个对象,就是在堆中申请了一块连续空间用来存放该对象。
= // 运算符,将引向o指向了对象。也就是说将栈中表示引用o的内存地址的内容改写成了Object对象在堆中的地址。

C++:
C++ 如果直接定义类,如classA a; a 存在栈上(也意味着复制了对象a在栈中),如果classA a = new classA就存在堆中。

初学Java时,在很长一段时间里,总觉得基本概念很模糊。后来才知道,在许多Java书中,把对象和对象的引用混为一谈。

如果分不清对象与对象引用,那实在没法很好地理解下面的面向对象技术,把自己的一点认识写下来,或许能让初学Java的朋友们少走一点弯路。

为便于说明,我们先定义一个简单的类:

class student

{

int name;

int age;

int sex;

}

有了这个类(模板),就可以用它来创建对象:student stu1 = new student();

通常把这条语句的动作称之为创建一个对象,其实,它包含了四个动作。

1)右边的"new student",是以student类为模板,在堆空间里创建一个student类的对象(也简称为student对象)。

2)末尾的()意味着,在对象创建后,立即调用student类的构造函数,对刚生成的对象进行初始化。

构造函数是肯定有的。如果你没写,Java会给你补上一个默认的构造函数。

3)左边的"student stu1"创建了一个student类引用变量。所谓student类引用,就是以后可以用来指向某个

student对象的对象引用,它指向的是某个student对象的内存地址(有点C语言中指针的味道)。

4)"="操作符使对象引用指向刚创建的那个student对象。

我们可以把这条语句拆成两部分:student stu1; stu1 = new student();效果是一样的。

这样写,就比较清楚了,有两个实体:一是对象引用变量(stu1),在Sun公司的实现中,对象的引用是一个句柄,其中包含一对指针:一个指针指向该对象的方法表,一个指向该对象的数据;另一个是对象本身(就是new出来的那个对象)。

在堆空间里创建的实体,与在数据段以及栈空间里创建的实体不同。尽管它们也是确确实实存在的实体,但是,我们看不见,也摸不着。不仅如此,我们仔细研究一下第二句,想想刚刚创建的student对象叫什么名字?

有人说,它叫"student"。不对,"student"是类(对象的创建模板)的名字。一个student类可以据此创建出无数个对象,这些对象不可能全叫"student"。对象连名都没有,没法直接访问它。我们只能通过对象引用来间接访问对象。

为了形象地说明对象、对象引用及它们之间的关系,可以做一个或许不很妥当的比喻:

对象好比是一只没有线的风筝,引用变量是一根线,可以用来系风筝。如果只执行了第一条语句,还没执行第二条,此时创建的引用变量stu1还没指向任何一个对象,它的值是null,引用变量可以指向某个对象,或者为null。这时stu1是一根线,一根还没有系上任何一个风筝的线。

执行了第二句后,一只新风筝做出来了,并被系在stu1这根线上。我们抓住这根线,就等于抓住了那只风筝。

再来一句:student stu2;就又做了一根线,还没系上风筝。如果再加一句:stu2=stu1;系上风筝了。

这里,发生了复制行为。但是,要说明的是,对象本身并没有被复制,被复制的只是对象引用。

结果是,stu2也指向了stu1所指向的对象,也就是两根线系的是同一只风筝。

如果用下句再创建一个对象:stu2=new student();则引用变量stu2改指向第二个对象。

从以上叙述再推演下去,我们可以获得以下结论:

(1)一个对象引用可以指向0个或1个对象(一根线可以不系风筝,也可以系一个风筝),而且可以改指;

(2)一个对象可以有N个引用指向它(可以有N条线系同一个风筝)。

如果有下面语句:stu1=stu2;

按上面的推断,stu1也指向了第二个对象。这个没问题。问题是第一个对象呢?没有一条线系住它,它飞了。

很多书里说,它被Java的垃圾回收机制回收了,这不确切,准确地说,它已成为Java垃圾回收机制的处理对象。

至于什么时候真正被回收,那要看垃圾回收机制的心情了。由此看来,new student();该语句应该不合法吧,

至少是没用的吧?不对,它是合法的,而且可用的。譬如,如果我们仅仅为了打印而生成一个对象,

就不需要用引用变量来系住它。最常见的就是打印字符串:System.out.println("I am Java!");

字符串对象"I am Java!"在打印后即被丢弃,有人把这种对象称之为临时对象。

---

最后再说明一下:

C++中:

Student student(20) ;//这里student是引用 对象分配在 栈空间中,这里只是我的理解

Student *student = new Student(20);//这里student是指针,new Student(20)是分配在堆内存空间的

但是在Java中

Student student(20) ;//注意:java中没有这样实例化对象的, 要想得到一个对象 必须要new出来.

Student student ;//这个只是定义了一个引用
,没有指向任何对象

Student student = new Student(20);//定义了一个引用 ,指向堆内存中的student对象

C++和JAVA实例化对象的区别的更多相关文章

  1. Java实例化对象过程中的内存分配

    Java实例化对象过程中的内存分配: https://blog.csdn.net/qq_36934826/article/details/82685791 问题引入这里先定义一个很不标准的“书”类,这 ...

  2. java实例化对象

    摘要:分享牛,分享牛分享,java类加载机制,java实例化对象,java实例化对象机制,java基础. java是如何实例化对象的呢?以及实例化对象的先后顺序是什么?下面我们以测试的方式说明. 1. ...

  3. java实例化对象的方式

    一.Java中创建(实例化)对象的五种方式  1.用new语句直接创建对象,这是最常见的创建对象的方法. 2.通过工厂方法返回对象,如:String str = String.valueOf(23); ...

  4. 转:java实例化对象的过程

    学习JAVA这门面向对象的语言,实质就是不断地创建类,并把类实例化为对象并调用方法.对于初学JAVA的人总搞清楚对象是如何实例化的,假如类之间存在继承关系,那就更糊涂了.下面我们通过两个例题来说明对象 ...

  5. javascript中使用new与不使用实例化对象的区别

    我们先来看个实例 function Me(name,age,job){ this.name = name; this.age = age; this.job = job; } 请问这以下两种实例化对象 ...

  6. java实例化对象的五种方法

    1.用new语句创建对象,这是最常见的创建对象的方法. 2.通过工厂方法返回对象,如:String str = String.valueOf(23); 3.运用反射手段,调用java.lang.Cla ...

  7. java实例化对象的几种方式

    这里一共整理了四种方法 ①用类的new ()创建 ②用clone方法创建, 需要类实现 Cloneable 接口 ③通过反射机制创建 ④将一个对象实例化后,进行序列化,再反序列化 下面是实现代码 1) ...

  8. java实例化对象的过程

    总结以上内容,可以得到对象初始化过程:  1. 如果存在继承关系,就先父类后子类:  2 .如果在类内有静态变量和静态块,就先静态后非静态,最后才是构造函数:  3 .继承关系中,必须要父类初始化完成 ...

  9. 一图看懂Spring获取对象与java new对象区别

    Spring获取对象与java new对象的区别,图片被压缩了,请点击图片放大查看

随机推荐

  1. javascript断点设置和调试

    JS调试必备的5个debug技巧http://www.jb51.net/article/47812.htm Chrome 中的 JavaScript 断点设置和调试技巧http://www.xuebu ...

  2. 删除Win10的OneDrive

    1.运行 -> gpedit.msc 计算机配置 -> 管理模板 -> Windows组件 -> OneDrive -> 禁止使用OneDrive进行文件储存 -> ...

  3. Unity3D中简单的C#异步Socket实现

    Unity3D中简单的C#异步Socket实现 简单的异步Socket实现..net框架自身提供了很完善的Socket底层.笔者在做Unity3D小东西的时候需要使用到Socket网络通信.于是决定自 ...

  4. Mybatis热加载Mapper.xml

    开发的时候,写Mybatis Mapper.xml文件的时候,每次修改SQL都需要重启服务,感觉十分麻烦,于是尝试写了一个Mybatis的Mapper.xml热加载. 能在修改Mapper.xml之后 ...

  5. golang模板语法简明教程

    [模板标签] 模板标签用"{{"和"}}"括起来   [注释] {{/* a comment */}} 使用“{{/*”和“*/}}”来包含注释内容   [变量 ...

  6. httpClient使用中报错org.apache.commons.httpclient.HttpMethodBase - Going to buffer response body of large or unknown size.

    在使用HttpClient发送请求,使用httpMethod.getResponseBodyAsString();时当返回值过大时会报错: org.apache.commons.httpclient. ...

  7. OceanBase分布式事务以及两阶段提交实现具体设计

    眼下OceanBase中还存在updaeserver单点,下一步的开发任务是使得OB支持多点写入,支持多个UPS(及updateserver). 当中难点是怎样设计两阶段提交的失败恢复以及多机的快照读 ...

  8. 开启GitHub模式,now!

    (原文地址为:http://www.karottc.com/blog/2014/06/15/current-doing/) 最近看到了一篇文章,该文章的作者将自己连续177天在github上commi ...

  9. 【转】VC下的Unicode编程

    转自http://www.leewei.org/?p=1304 UniCode简述 在Windows下用VC编程,如果编写的程序要在多种语言环境下运行(比如日文.中文.葡萄牙文等),使用VC默认的MB ...

  10. Reactjs中的相关机制

    http://blog.csdn.net/cengjingcanghai123/article/details/48480473 https://segmentfault.com/a/11900000 ...