关于java8中的String
- String 对象的不可变性
java8中的String只有2个属性value和hash,相关代码如下:
/** The value is used for character storage. */
private final char value[]; /** Cache the hash code for the string */
private int hash; // Default to 0
value是字符串的字符数组,hash是字符串的hash值缓存
public final class String
implements java.io.Serializable, Comparable<String>, CharSequence
其中String 类被 final 关键字修饰了,而且变量 char 数组也被 final 修饰了。
我们知道类被 final 修饰代表该类不可继承,而 char[] 被 final+private 修饰,代表了 String 对象不可被更改。Java 实现的这个特性叫作 String 对象的不可变性,即 String 对象一旦创建成功,就不能再对它进行改变。
- Java 这样做的好处在哪里呢?
第一,保证 String 对象的安全性。假设 String 对象是可变的,那么 String 对象将可能被恶意修改。
第二,保证 hash 属性值不会频繁变更,确保了唯一性,使得类似 HashMap 容器才能实现相应的 key-value 缓存功能。
第三,可以实现字符串常量池。在 Java 中,通常有两种创建字符串对象的方式,一种是通过字符串常量的方式创建,如 String str=“abc”;另一种是字符串变量通过 new 形式的创建,如 String str = new String(“abc”)。
当代码中使用第一种方式创建字符串对象时,JVM 首先会检查该对象是否在字符串常量池中,如果在,就返回该对象引用,否则新的字符串将在常量池中被创建。这种方式可以减少同一个值的字符串对象的重复创建,节约内存。
String str = new String(“abc”) 这种方式,首先在编译类文件时,"abc"常量字符串将会放入到常量结构中,在类加载时,“abc"将会在常量池中创建;其次,在调用 new 时,JVM 命令将会调用 String 的构造函数,同时引用常量池中的"abc” 字符串,在堆内存中创建一个 String 对象;最后,str 将引用 String 对象。
- 平时对String的误解
平常编程时,对一个 String 对象 str 赋值“hello”,然后又让 str 值为“world”,这个时候 str 的值变成了“world”。那么 str 值确实改变了,为什么我还说 String 对象不可变呢?
在 Java 中要比较两个对象是否相等,往往是用 ==,而要判断两个对象的值是否相等,则需要用 equals 方法来判断。
这是因为 str 只是 String 对象的引用,并不是对象本身。对象在内存中是一块内存地址,str 则是一个指向该内存地址的引用。所以在刚刚我们说的这个例子中,第一次赋值的时候,创建了一个“hello”对象,str 引用指向“hello”地址;第二次赋值的时候,又重新创建了一个对象“world”,str 引用指向了“world”,但“hello”对象依然存在于内存中。也就是说 str 并不是对象,而只是一个对象引用。真正的对象依然还在内存中,没有被改变。
- String.intern 的原理
首先看下面这段代码及其结果:
在字符串常量中,默认会将对象放入常量池;在字符串变量中,对象是会创建在堆内存中,同时也会在常量池中创建一个字符串对象,复制到堆内存对象中,并返回堆内存对象引用。
如果调用 intern 方法,会去查看字符串常量池中是否有等于该对象的字符串,如果没有,就在常量池中新增该对象,并返回该对象引用;如果有,就返回常量池中的字符串引用。堆内存中原有的对象由于没有引用指向它,将会通过垃圾回收器回收。
使用 intern 方法需要注意的一点是,一定要结合实际场景。因为常量池的实现是类似于一个 HashTable 的实现方式,HashTable 存储的数据越大,遍历的时间复杂度就会增加。如果数据过大,会增加整个字符串常量池的负担。
关于java8中的String的更多相关文章
- java8中map的meger方法的使用
java8中map有一个merge方法使用示例: /** * 打印出包含号码集的label的集合 * * @param args */ public static void main(String[] ...
- java8中CAS的增强
注:ifeve.com的同名文章为本人所发,此文在其基础做了些调整.转载请注明出处! 一.java8中CAS的增强 前些天,我偶然地将之前写的用来测试AtomicInteger和synchronize ...
- java8中的map和reduce
java8中的map和reduce 标签: java8函数式mapreduce 2014-06-19 19:14 10330人阅读 评论(4) 收藏 举报 分类: java(47) FP(2) ...
- Java8中Lambda表达式的10个例子
Java8中Lambda表达式的10个例子 例1 用Lambda表达式实现Runnable接口 //Before Java 8: new Thread(new Runnable() { @Overri ...
- 初探Java8中的HashMap(转)
HashMap是我们最常用的集合之一,同时Java8也提升了HashMap的性能.本着学习的原则,在这探讨一下HashMap. 原理 简单讲解下HashMap的原理:HashMap基于Hash算法,我 ...
- 谈一谈Java8的函数式编程(二) --Java8中的流
流与集合 众所周知,日常开发与操作中涉及到集合的操作相当频繁,而java中对于集合的操作又是相当麻烦.这里你可能就有疑问了,我感觉平常开发的时候操作集合时不麻烦呀?那下面我们从一个例子说起. 计 ...
- java8中Lambda表达式和Stream API
一.Lambda表达式 1.语法格式 Lambda是匿名函数,可以传递代码.使用“->”操作符,改操作符将lambda分成两部分: 左侧:指定了 Lambda 表达式需要的所有参数 右侧:指定了 ...
- java8中的接口与时间操作
java8中接口可以有默认方法(用default修饰,可以有多个)和静态方法了. public interface Tran { default public String getName() { r ...
- Java8中的 lambda 和Stream API
前言 由于项目中用到了比较多有关于 Java8 中新的东西,一开始自己只是会写,但是写起来不太顺,然后就在网上找到了一个很好的关于Java8新特性的视频,所以就进行了学习了一下,以下是自己对 la ...
随机推荐
- 2018/7/31-zznu-oj-问题 F: 手机密码--【裸dfs+for循环即可!——据说三个小时内只有两个人读完了题意并轻松AC了】
问题 F: 手机密码 时间限制: 1 Sec 内存限制: 128 MB提交: 41 解决: 23[提交] [状态] [讨论版] [命题人:admin] 题目描述 手机安全问题是大家经常关心的一个问 ...
- go语言defer关键字背后的实现,语法,用法
原文: https://tiancaiamao.gitbooks.io/go-internals/content/zh/03.4.html ------------------------------ ...
- ASP.NET MVC QQ互联接入
ASP.NET MVC QQ Connect 介绍 ASP.NET MVC QQ互联接入Demo. 项目地址:https://gitee.com/Liu_Cabbage/ASP.NET-MVC-QQ- ...
- 洛谷P1273 有线电视网【树形dp】
题目:https://www.luogu.org/problemnew/show/P1273 题意:一棵树,叶子节点是用户,每天边有一个权值表示花费,每一个用户有一个值表示他们会交的钱. 问在不亏本的 ...
- Codeforces Round #543 (Div. 1, based on Technocup 2019 Final Round) 题解
题面戳这里 A. Diana and Liana 首先如果s>ks>ks>k一定无解,特判一下.那么我们考虑找恰好满足满足题目中的要求的区间[l,r][l,r][l,r],那么需要要 ...
- 最后执行finally
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...
- [Google Guava] 排序: Guava强大的”流畅风格比较器”
原文链接 译者: 沈义扬 排序器[Ordering]是Guava流畅风格比较器[Comparator]的实现,它可以用来为构建复杂的比较器,以完成集合排序的功能. 从实现上说,Ordering实例就是 ...
- 【题解】狼和羊-C++
Description 米基家的后院养着一群羊,米基由于疲劳睡着了,这时一群饿狼钻进了后院开始攻击羊群,后院是由许多个方格构成的长方形区域,每个方格中用字符'?'表示空地,'#'表示栅栏,'o'表示羊 ...
- ueditor+word粘贴上传!
图片的复制无非有两种方法,一种是图片直接上传到服务器,另外一种转换成二进制流的base64码 目前限chrome浏览器使用,但是项目要求需要支持所有的浏览器,包括Windows和macOS系统.没有办 ...
- 2019 Multi-University Training Contest 10
目录 Contest Info Solutions C - Valentine's Day D - Play Games with Rounddog E - Welcome Party G - Clo ...