首页
学习
活动
专区
工具
TVP
发布
精选内容/技术社群/优惠产品,尽在小程序
立即前往

为什么新的String("a")== new String("a")给出false而"a"=="a"给出true.为什么看起来它们在后来的情况下都被视为同一个实例?

这个问题涉及到Java编程语言中的String对象的创建方式和比较方式。

在Java中,String对象有两种创建方式:

  1. 字符串字面量:直接在代码中使用双引号括起来的字符串,例如"a"。这种方式创建的String对象会被存储在字符串常量池中。
  2. 使用String构造函数:例如new String("a")。这种方式创建的String对象会在堆内存中创建一个新的对象。

对于字符串比较,Java中有两种方式:

  1. 使用"=="运算符:这种方式比较的是两个对象的引用是否相同,也就是说它们是否指向同一个内存地址。
  2. 使用equals()方法:这种方式比较的是两个对象的内容是否相同,也就是说它们的值是否相等。

在这个问题中,"a"=="a"给出的结果是true,因为Java编译器会将同一个字符串字面量的引用指向同一个内存地址,所以它们的引用是相同的。

而new String("a")== new String("a")给出的结果是false,因为使用String构造函数创建的对象是在堆内存中创建的,每次创建都会在堆内存中创建一个新的对象,所以它们的引用是不同的。

这个问题中的问题在于,它假设了两种不同的创建方式创建的String对象都是同一个实例,这是不正确的。每种创建方式都会创建不同的String对象,它们的引用是不同的,即使它们的内容相同。因此,我们不能将它们视为同一个实例。

页面内容是否对你有帮助?
有帮助
没帮助

相关·内容

  • Java到底是不是一种纯面向对象语言?

    但是在后来,我互联网站上陆续看到不少开发者说 “Java实际上不是纯粹面向对象,因为并不是所有的东西 Java 世界都是一个对象”。...到了更后来一次JVM学习过程中,我有了发现: JVM 创建对象时候,实际上会创建两个对象: 一个是实例对象。 另一个是Class 对象。...这也揭开了另一个迷:为什么静态内容一个对象中(不管是emp还是emp2)改变了,另一个对象中也同时改变,因为这两个对象改变都是 Employee.class 同一个对象里面的内容。...以上都说明,JVM内部,其实原始类型就是对象。 那么,既然说 “JVM”会为所有的基本类型创建一个对象,那我们为什么还那么常用 “原始类型”, 不是直接使用对应包装类对象呢?...Integer(3) == new Integer(3); // false new Integer(100) == new Integer(100); // false Integer.valueOf

    889110

    Java是一种纯面向对象语言吗?

    但是在后来,我互联网站上陆续看到不少开发者说 “Java实际上不是纯粹面向对象,因为并不是所有的东西 Java 世界都是一个对象”。...到了更后来一次JVM学习过程中,我有了发现: JVM 创建对象时候,实际上会创建两个对象: 一个是实例对象。 另一个是Class 对象。...这也揭开了另一个迷:为什么静态内容一个对象中(不管是emp还是emp2)改变了,另一个对象中也同时改变,因为这两个对象改变都是 Employee.class 同一个对象里面的内容。...以上都说明,JVM内部,其实原始类型就是对象。 那么,既然说 “JVM”会为所有的基本类型创建一个对象,那我们为什么还那么常用 “原始类型”, 不是直接使用对应包装类对象呢?...Integer(3) == new Integer(3); // false new Integer(100) == new Integer(100); // false Integer.valueOf

    1K00

    ​第3章 对于所有对象都通用方法

    第8条 覆盖equals时请遵守通用约定 不覆盖equals 不覆盖equals情况下,类每个实例都与它自身相等,如果满足以下任何一个条件,就是所期望结果: 类每个实例本质上都是唯一 不关心类是否提供了...: 逻辑相等,就是逻辑上是相等,比如id一样,判定它们相等,即使它们是两个不同对象 什么时候应该覆盖equals 当类需要逻辑相等这个概念时候就应该覆盖equals 比如要判断两个student是否是同一个人...Object通用约定(Object类中注释即是): 应用程序执行期间,只要对象equals方法比较操作所用到信息没有被修改,那么对这同一个对象调用多次,hashCode方法都必须始终如一地返回同一个整数....同一个应用程序多次执行过程中,每次执行所返回整数可以不一致....return new OkHttpCall(serviceMethod, args); } PS:使用优秀开源库时候,如果可以,多看看它源码,你会学到很多!

    51920

    大话 JavaScript(Speaking JavaScript):第六章到第十章

    它们需要语句但不需要语句情况下很有用。在这种情况下,通常也允许块。...块之后,有一个空语句。 陷阱:ASI 可能意外地不会被触发 有时,行中语句以允许作为前一语句延续标记开头。然后,尽管看起来应该被触发,但 ASI 不会被触发。...以下部分详细解释了严格模式特性。通常情况下,您不需要了解它们,因为您大多数情况下会因为您本不应该做事情得到更多警告。 变量必须在严格模式下声明 严格模式下,所有变量必须明确声明。...以下值被转换为false它们被称为“假值”: undefined,null false 0,NaN '' 所有其他值都被视为“真值”,并转换为true(包括所有对象!)。...> typeof Boolean(false) // no change 'boolean' new Boolean(bool) 作为构造函数,它创建了Boolean实例(参见原始包装对象),一个将

    30910

    每个java初学者都应该搞懂问题

    但不好理解地方是: String a=new String("foo"); String b=new String("foo"); 则a==b将返回false。...也就说,多次调用上面的构造器创建多个对象,他们String类型属性s都指向同一个对象。 上面的结论还基于这样一个事实:对于字符串常量,如果内容相同,JAVA认为它们代表同一个String对象。...而用关键字new调用构造器,总是会创建一个对象,无论内容是否相同。 至于为什么要把String类设计成不可变类,是它用途决定。其实不只String,很多JAVA标准类库中类都是不可变。...instance属性创建实例时候初始化,static属性类加载,也就是第一次用到这个类时候初始化,对于后来实例创建,不再次进行初始化。这个问题会在以后系列中进行详细讨论。...bill) 所以,使用instanceof绝大多数情况下并不是推荐做法,应当好好利用多态。

    38731

    (Java实习生)每日10道面试题打卡——Java基础知识篇「建议收藏」

    洗衣机(Machine):Machine洗衣机洗衣服这个程序任务中有两个作用,分别是清洗、烘干。 从上面这个例子能看出,面向过程编程方式比较直接且高效,面向对象编程方式更易复用、扩展和维护!...2、请你简述一下面向对象三个基本特征? 继承:承是Java中面向对象最显著一个特征,继承是从已有的类中派生出新类,类可以吸收已有的属性、行为,并扩展能力。...多态:封装和继承都是为多态来服务,多态是指同一个行为具有多个不同表现形式。Java中方法重载和重写是实现多态2种方式。...规范中并没有给出其储存大小,《Java虚拟机规范》中给出了4个字节,和boolean数组1个字节定义,具体还要看虚拟机实现是否按照规范来,所以1个字节、4个字节都是有可能。...Student stu2 = new Student("Jimmy",24); System.out.println("两位同学是同一个人吗?"

    38020

    来挑战下这 10 个 Python 问题

    在上面的示例中,函数定义期间,Python 允许引用尚未定义类或函数。但是,执行期间,A 已经是 int 类,这意味着函数方法将返回一个新创建 int 实例,int 实例默认值就是 0。...:16: 对象函数查找顺序是:实例级别 > 类级别 > 父类级别,上面的代码,初始化时绑定函数就是实例级别,类内部定义就是类级别。...在上述所有情况下,空字符串都被视为空序列,因此 sum 将简单地将起始参数作为总结果返回。第一种情况下,它默认为零,对于第二种和第三种情况,它意味着空列表和字典作为开始参数传入。...9、见过负数 0.0 max(-0.0, 0.0) 为什么会这样?出现这种情况是由于两个原因。负零和零 Python 中被视为相等。max 逻辑是,如果多个最大值,返回遇到第一个。...10、违反数学规则 >>> x = (1 << 53) + 1 >>> x + 1.0 > x False 正确结果是 False,这违反了数学规则啊,为什么呢?

    49410

    JavaSE面试深度剖析 第二讲

    ,其实保留字这个词应该有更广泛意义,因为熟悉 C 语言程序员都知道,系统类库中使用过有特殊意义单词或单词组合都被视为保留字。...这时,应该考虑使用StringBuffer 类,它允许修改,不是每个不同字符串都要生成一个对象。并且,这两种类对象转换十分容易。...也就说,多次调用上面的构造器创建多个对象,他们 String 类型属性 s 都指向同一个对象。...上面的结论还基于这样一个事实:对于字符串常量,如果内容相同,Java 认为它们代表同一个 String 对象。而用关键字 new 调用构造器,总是会创建一个对象,无论内容是否相同。...至于为什么要把 String 类设计成不可变类,是它用途决定。其实不只 String,很多 Java 标准类库中类都是不可变

    51810

    String三姐妹你所不知道坑!

    主要作用在于一个对象需要被多进程共享,并且频繁访问时,可以省略同步和锁等待时间,从而增加系统性能 2.针对常量池优化:当两个String对象有用相同值时,他们只引用常量池中同一个拷贝。...如以上程序,我们很容易直到结果是true,false,true.具体内存分配方式如下图: ? 3.类final化:即不可能有任何子类,会提高安全性。...StringBuffer和StringBuilder ◆ ◆ ◆ ◆ 由于String对象不可变,所以修改操作时,会频繁创建对象,性能相对较差,于是就产生了StringBuffer和StringBuilder...StringBuffer和StringBuilder差别就是,StringBuffer是线程安全 StringBuilder是非线程安全 需要关注是,由于它们对象是可变创建时候最好先预估量级...当时小明同学脑中是觉得String会创建很多对象,然后再拼接,肯定是第一个慢! 之后面试官露出一个诡异笑容……告诉我,第一个时间快,并且速度接近为0! 当时我就震惊了! 这是为什么呢!

    37320

    重学JS基础--数据类型

    js中除了上面的基本类型之外就是引用类型了,也可以说就是对象了,Object,Function等(这里注意,Array.Date都被归为了Object类型),它们栈空间中存是一个指针,指向是存在堆空间里面的值...引用类型比较是引用比较 var person1 = {}; var person2 = {}; console.log(person1 == person2)//false 为什么两个对象看起来一摸一样...所以当第二行代码访问s1时候,后台会自动完成下列操作: var s1 = new String("helloworld"); //创建String类型一个实例; var s2 = s1.substr...(4); //实例上调用指定方法; s1 = null; //销毁这个实例; 正因为有第三步这个销毁动作,所以你应该能够明白为什么基本数据类型不可以添加属性和方法...,这也正是基本装包类型和引用类型主要区别:对象生存期 使用new操作符创建引用类型实例执行流离开当前作用域之前都是一直保存在内存中 自动创建基本包装类型对象,则只存在于一行代码执行瞬间

    75810

    freeswitch笔记(4)-esl inbound模式重连及内存泄露问题

    参考上图,if条件这行打一个断点,然后利用调试工具,断点处,强制把inboundClient.authenticated改成false(不清楚该调试技巧同学,可参考之前旧文idea 高级调试技巧...,继续运行到connect后,还是13516进程,又建立了1个连接(对应随机端口号为58857),之前旧连接(58825)并没有释放,哪怕这里我用new Client()生成了一个全新实例,旧实例关联连接资源仍然...4) 继续这样操作,会发现每次都会创建1个链接,原来链接依然存在。...按该网友建议,改成static静态实例后,保证只有1个实例就可以了。细节不多说,代码最后会给出,这里谈另一个问题: ?...线程池最大线程数是MAX_VALUE,相当于没有上限,如果异常情况下,线程会一直上涨,直到资源用完, 最好换成明确有上限写法。

    2.4K31

    Java编程思想读书笔记(二)【一切都是对象】

    2.1 用引用操纵对象 每种编程语言都有自己操纵内存元素方式 操纵内存元素方式:直接操纵元素、基于特殊语法间接表示(如C和C++里指针)操纵元素 Java中,一切都被视为对象,操纵对象标识符是引用...常量通常直接存放在程序代码内部,这样做是安全,因为它们永远不会被改变。 嵌入式系统中,常量本身会和其他部分隔离开,所有这种情况下,可以选择将其存放在ROM(只读存储器)中。...“持久化对象”中,对象被存放于磁盘上,因此,即使程序终止,它们仍可以保持自己状态。 堆栈是栈。(重要事情说三遍,这是第二遍) 堆栈指针若向下移动,则分配内存;若向上移动,则释放那些内存。...2.4 创建数据类型:类 大多数面向对象程序设计语言习惯用关键子class来表示“我准备告诉你一种类型对象看起来像什么样子。...一种情形是,只想为某特定域分配单一存储空间,不去考虑究竟要创建多少对象,甚至根本就不创建任何对象。 另一种情形是,希望某个方法不与包含它那个类任何对象实例关联在一起。

    33720

    Java六大问题你都懂了吗?

    instance属性创建实例时候初始化,static属性类加载,也就是第一次用到这个类时候初始化,对于后来实例创建,不再次进行初始化。这个问题会在以后系列中进行详细讨论。...a和b值其实是两个不同内存地址值,所以使用"=="操作符,结果会是false.诚然,a和b所指对象,它们内容都是"foo",应该是"相等",但是==操作符并不涉及到对象内容比较。...这时,应该考虑使用StringBuffer类,它允许修改,不是每个不同字符串都要生成一个对象。并且,这两种类对象转换十分容易。...也就说,多次调用上面的构造器创建多个对象,他们String类型属性s都指向同一个对象。上面的结论还基于这样一个事实:对于字符串常量,如果内容相同,Java认为它们代表同一个String对象。...而用关键字new调用构造器,总是会创建一个对象,无论内容是否相同。至于为什么要把String类设计成不可变类,是它用途决定。其实不只String,很多Java标准类库中类都是不可变

    29640

    String类和常量池内存分析例子以及8种基本类型

    根据《java虚拟机规范 Java SE 8版》记录,如果某String实例所包含Unicode码点序列与CONSTANT——String_info结构所给出序列相同,之前又曾在该实例上面调用过String.intern...意思就是,使用 String.intern() 方法时,如果已经存在一个字符串实例(已经调用过 intern() 实例),那么 intern() 方法将返回该已存在字符串实例引用,不是创建一个字符串实例...通过这个例子,我们可以看到,当多次调用 intern() 方法时,如果已经存在相同内容字符串实例,那么将返回相同实例引用,不是创建实例。...ss1 + ss2 == s3比较中,ss1 和 ss2 是 final 变量,编译器会将它们视为编译时常量,并在编译期间计算它们值。...Integer i1 = new Integer(40) ;这种情况下会创建对象。

    18310

    最有价值50道java面试题(一)

    默认对于同一个包中其他类相当于公开(public),对于不是同一个包中其他类相当于私有(private)。...,因此有些地方将其称之为保留字,其实保留字这个词应该有更广泛意义,因为熟悉C语言程序员都知道,系统类库中使用过有特殊意义单词或单词组合都被视为保留字) 7、int 和Integer 有什么区别...,如果字面量-128到127之间,那么不会newInteger对象,而是直接引用常量池中Integer对象,所以上面的面试题中f1==f2结果是true,f3==f4结果是false。...String str = new String(“hello”); 上面的语句中str放在栈上,用new创建出来字符串对象放在堆上,“hello”这个字面量放在静态存储区。...答:Static Nested Class是被声明为静态(static)内部类,它可以不依赖于外部类实例实例化。通常内部类需要在外部类实例化后才能实例化,其语法看起来挺诡异,如下所示。

    981101

    记一次离谱内存马 GetShell

    安全工具没有覆盖情况下处理思路和解决办法,经过一番挣扎和尝试后,最终绕过种种限制获取了 webshell。...② Agent 马 - 耻辱失败 在这种代码看起来是执行了,但是不知道为什么回显不成功,内存马也没打进去情况下,最好方式是使用 Java Agent 马进行利用。...调试过程比我想想时间要长,里面坑点很多。这里不一一贴代码赘述,直接给出一些关键技术点以及坑点。 ① IBM J9 实例化校验机制?...在内存马测试过程中,出现了一个令人难以置信问题:使用同一个 ClassLoader define 成功并且返回 Class,竟然无法使用 newInstance() 创建类实例。 太离谱了!...后来搜索开源 OpenJ9 源代码,发现代码结构改动也比较大,看起来不具有太多参考性。

    20510

    JAVA笔试题_javabean面试题

    无法使用关键字,因此有些地方将其称之为保留字,其实保留字这个词应该有更广泛意义,因为熟悉 C 语言程 序员都知道,系统类库中使用过有特殊意义单词或单词组合都被视为保留字。...这时,应该考虑使用 StringBuffer 类,它允许修改,不是每个 不同字符串都要生成一个对象。并且,这两种类对象转换十分容易。...s = "Initial Value"; ... } 而非 s = new String("Initial Value"); ​ 后者每次都会调用构造器,生成对象,性能低下且内存开销大,并且没有意义...也就说,多次调用上面的构造器创建多个对象,他 们 String 类型属性 s 都指向同一个对象。 ​...上面的结论还基于这样一个事实:对于字符串常量,如果内容相同,Java 认为它们代表同一个 String 对象。 用关键字 new 调用构造器,总是会创建一个对象,无论内容是否相同。

    49730

    Java基础面试题整理「建议收藏」

    当然可以,比如final Person[] persons = new Persion[]{}.persons是不可变对象引用,但其数组中Person实例却是可变.这种情况下需要特别谨慎,不要共享可变对象引用...,只有当 a 和 b 指向是堆中同一个对象才会返回 true. a.equals(b) 是进行内容比较,其比较结果取决于equals()具体实现.多数情况下,我们需要重写该方法,如String 类重写...String s = new String("abc")创建了几个String对象? 2个.一个是字符串字面常数,字符串常量池中;另一个是new出来字符串对象,堆中....s2直接优化为”ab”,将其放置常量池当中;s5则是被创建在堆区,相当于s5=new String(“ab”); 你对String对象intern()熟悉么?...StringBuffer是对象本身操作,不是产生对象,因此在有大量拼接情况下,我们建议使用StringBuffer(线程安全).

    40910
    领券