JAVA基础学习之路(八)[1]String类的基本特点
String类的两种定义方式:
直接赋值
通过构造方法赋值
//直接赋值
public class test2 {
public static void main(String args[]) {
String str = "hello";
System.out.println(str);
}
} //通过构造方法
public class test2 {
public static void main(String args[]) {
String str = new String("hello");
System.out.println(str);
}
}
但是,两种方法却有着极大的区别
主要体现在内存上
一个简单的例子:
public class test1 {
public static void main(String args[]) {
int a = 10;
int b = 10;
String str_1 = "hello";
String str_2 = "hello";
String str_3 = new String("hello");
System.out.println(a==b);
System.out.println(str_1==str_2);
System.out.println(str_1==str_3);
System.out.println(str_2==str_3);
}
} //输出为true true false false
按道理来说,应该是四个true,因为他们的值都是相等的啊.......但是.....

上图解释了两个通过直接赋相同值产生的字符串使用“”==“”为什么返回true。
为什么会全部指向一块堆内存而不是分别指向自己的堆内存呢???
共享设计模式:
在JVM底层有一个对象池,里面有包括String在内的许多对象,当代码之中使用了直接赋值的方式定义了一个String类对象时,会将此字符串使用的匿名对象加入对象池。之后若有采用直接赋值的方式定义字符串,并且赋了相同的值,那么不会开辟新的堆内存空间,而是使用已有的对象(堆内存)进行继续使用。

上图解释了为什么直接赋值和构造方法赋相同的值,然而返回值却为false。因为使用构造方法定义字符串,使用了new关键字,意味着产生一块新的堆内存。那么两种方法各自开辟了一块堆内存,“==”符号对于字符串来说,比较的是地址值。两块堆内存的地址不同,所以返回值为false。
若要比较字符串的内容,而不是地址,应该使用str_a.equals(str_b)
字符串常量就是String类的匿名对象,所谓的直接赋值实际上就是为匿名对象加了一个名字。但是String类的匿名对象是由系统自动生成的,不用用户自己创建
public class test1 {
public static void main(String args[]) {
String str = "hello";
System.out.println("hello".equals(str));
}
}
//返回值为true
tips:
防止空指向异常(使用了未实例化的对象):将字符串写在输入的前面
public class test1 {
public static void main(String args[]) {
String input = null;
System.out.println(input.equals("hello"));
}
}
//Exception in thread "main" java.lang.NullPointerException
at test.test1.main(test1.java:6) 空指向异常
public class test1 {
public static void main(String args[]) {
String input = null;
System.out.println("hello".equals(input));
}
}
//false
两种定义方法的优劣:
直接赋值节约空间
然而构造方法却会产生大量垃圾,如下图:

代码从右向左看,产生的第一块堆内存会成为垃圾
构造方法实例化的方法除了浪费内存外,其定义的对象不会保存在对象池之中,若要保存,需要手动入池(使用inner()方法)
public class test1 {
public static void main(String args[]) {
String str_1 = new String("hello").intern();
String str_2 = "hello";
System.out.println(str_1==str_2);
}
}
//true
返回值为true,证明入池成功。
JAVA基础学习之路(八)[1]String类的基本特点的更多相关文章
- JAVA基础学习之路(三)类定义及构造方法
类的定义及使用 一,类的定义 class Book {//定义一个类 int price;//定义一个属性 int num; public static int getMonney(int price ...
- Java基础系列2:深入理解String类
Java基础系列2:深入理解String类 String是Java中最为常用的数据类型之一,也是面试中比较常被问到的基础知识点,本篇就聊聊Java中的String.主要包括如下的五个内容: Strin ...
- JAVA基础学习之路(一)基本概念及运算符
JAVA基础概念: PATH: path属于操作系统的属性,是系统用来搜寻可执行文件的路径 CALSSPATH: java程序解释类文件时加载文件的路径 注释: 单行注释 // 多行注释 /*... ...
- JAVA基础学习之路(十一)引用传递
引用传递: 不同栈内存可以指向同一块堆内存,不同栈内存可以对一块堆内存进行修改 范例一: class Message { private int num = 10; public Message(in ...
- Java基础篇(02):特殊的String类,和相关扩展API
本文源码:GitHub·点这里 || GitEE·点这里 一.String类简介 1.基础简介 字符串是一个特殊的数据类型,属于引用类型.String类在Java中使用关键字final修饰,所以这个类 ...
- JAVA基础学习之路(九)[2]String类常用方法
字符与字符串: 1.将字符数组变为字符串(构造方法) public String(char[] value) Allocates a new String so that it represents ...
- Java基础学习笔记十八 异常处理
什么是异常?Java代码在运行时期发生的问题就是异常. 在Java中,把异常信息封装成了一个类.当出现了问题时,就会创建异常类对象并抛出异常相关的信息(如异常出现的位置.原因等). 异常的继承体系 在 ...
- JAVA基础学习之路(五)数组的定义及使用
什么是数组:就是一堆相同类型的数据放一堆(一组相关变量的集合) 定义语法: 1.声明并开辟数组 数据类型 数组名[] = new 数据类型[长度]: 2.分布完成 声明数组:数据类型 数组名 [] = ...
- JAVA基础学习之路(七)对象数组的定义及使用
两种定义方式: 1.动态初始化: 定义并开辟数组:类名称 对象数组名[] = new 类名称[长度] 分布按成:类名称 对象数组名[] = null: 对象数组名 = new 类名称[长度]: 2 ...
随机推荐
- EF Core如何输出日志到Visual Studio的输出窗口
我们在使用EF Core的时候,很多时候需要在Visual Studio的输出窗口中知道EF Core在后台生成的SQL语句是什么,这个需求可以通过自定义EF Core的ILoggerFactory和 ...
- 由Oracle 11g SYSAUX 和 SYSTEM 表空间回收引发的联想
0x00--目的 整理一下以前一个SYSTEM表空间和SYSAUX表空间使用率达到99%上限的处理思路和相关知识点,好记性不如烂笔头 0x01--表空间使用率现状 通过查询可得知目前表空间使用情况如下 ...
- 03 Oracle分区表
Oracle分区表 先说句题外话… 欢迎成都天府软件园的小伙伴来面基交流经验~ 一:什么是分区(Partition)? 分区是将一个表或索引物理地分解为多个更小.更可管理的部分. 分区对应用透 ...
- iOS universallinks唤醒app
从iOS9之后,苹果就推出了这个功能,用来唤醒外部app.这个功能在那些电商app上使用尤其广泛,当你打开对应的h5网页后,上面跳出一个是否跳转app的按钮. 现在iOS11已经基本覆盖,iOS12也 ...
- 竞赛题解 - Ikki's Story IV-Panda's Trick
Ikki's Story IV-Panda's Trick - 竞赛题解 也算是2-sat学习的一个节点吧 终于能够自己解决一道2-sat的题了 ·题目 一个圆上有n个点按顺时针编号为 0~n-1 , ...
- Ubuntu Linux TinySerial串口调试助手 可视化界面 安装使用
ubuntu Linux下串口调试助手使用 Tiny Serial为一个开源项目,欢迎大家使用,基于Qt开发的串口调试助手,有一般串口助手的基本功能,更多功能正在完善. Github地址:https: ...
- rails 启动测试环境出现 "Rack::Cors" => Rack::Cors,解决方法
找到项目中"Rack::Cors"改为 Rack::Cors
- (杭电 1014)Uniform Generator
Uniform Generator Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others)To ...
- 北京Uber优步司机奖励政策(4月2日)
滴快车单单2.5倍,注册地址:http://www.udache.com/ 如何注册Uber司机(全国版最新最详细注册流程)/月入2万/不用抢单:http://www.cnblogs.com/mfry ...
- 深圳Uber优步司机奖励政策(1月4日~1月10日)
滴快车单单2.5倍,注册地址:http://www.udache.com/ 如何注册Uber司机(全国版最新最详细注册流程)/月入2万/不用抢单:http://www.cnblogs.com/mfry ...