Java中String特性

简介: 记一次逗比的操作

Java的String的传递


写一篇记录前几天遇到的个小问题,这个问题说起来很尴尬,还挺基础的。公司的Java项目的代码都要严格按照checkStyle约定的规范编写,不符合规范就会打包报错。


所以遇到复杂的逻辑只能拆分成数个子函数进行处理,拆分成子函数就会有一些参数割裂开,比如主函数逻辑里的一些字符串了,Map了,List了诸如此类的子函数要想用必须用参数传递的方式传到子函数里。这里就要注意String字符串的传递。


先看一段代码,stackoverflow上说很多人会回答错程序的输出。

publicstaticvoidmain(String[] args) {
Stringx=newString("ab");
change(x);
System.out.println(x);
}
publicstaticvoidchange(Stringx) {
x="cd";
}

如果你觉得是cd那这篇没白看,答案是ab。


那么这这段程序到底执行了什么,首先当"ab"创建后,Jvm在堆中分配对象所需内存空间。然后栈中的变量x指向了"ab"。


x保存了一个指向String对象的地址。x只是保存一个内存地址。在Java中只有值传递。当x通过参数传递给change()方法后,x被拷贝了一份,此时指向的内存地址还是跟主方法是一致的。接着change()创建了另一个对象"cd",并且将x指向了不同的地址空间。这时change()方法里的x就指向了"cd"。与主方法的对象就不是一个对象了。


image.png

上面的问题跟String的不可变没有关系。即使是StringBuilder,结果也一样。关键是变量存储的是引用,意思是在方法里改变了变量的引用地址,后续无论做什么改变都不会影响最初进来引用对象。


所以对于String字符串传递的情况只要保证进来的参数指向不发生变化即可,比如可以把change函数改成StringBuilder参数。


publicstaticvoidchange(StringBuilderx) {
x.delete(0, 2).append("cd");
}


String原理

首先String本质上是一个字符串数组,用final修饰所以String有以下特性


String的特性

  1. 不变性:String 是只读字符串,是一个典型的 immutable 对象,对它进行任何操作,其实都是创建一个新的对象,再把引用指向该对象。不变模式的主要作用在于当一个对象需要被多线程共享并频繁访问时,保证字符串堆不可变,可以保证线程之间的数据一致性。
  2. 常量池优化:String 对象创建之后,会在字符串常量池中进行缓存,如果下次创建同样的对象时,会直接返回缓存的引用。
  3. final:使用 final关键字来定义 String 类,表示 String 类不能被继承,提高了系统的安全性

String为什么用final修饰

  1. 为了安全和性能
  2. 字符串共享是解决内存消耗以及庞大性能消耗的必然选择。共享就会出现线程安全性。为了保证线程安全性,让String不可修改


String与StringBuilder与StringBuffer

  1. String内部用final修饰,不可变
  2. StringBuilder效率较高与StringBuffer,毕竟线程不安全
  3. StringBuffer线程安全、内部用Synchrinzed修饰







相关文章
|
2天前
|
Java 索引
String字符串常用函数以及示例 JAVA基础
String字符串常用函数以及示例 JAVA基础
|
3天前
|
Java 编译器 ice
【Java开发指南 | 第十五篇】Java Character 类、String 类
【Java开发指南 | 第十五篇】Java Character 类、String 类
23 1
|
1天前
|
Java API
Java 8新特性之Lambda表达式与Stream API
【5月更文挑战第17天】本文将介绍Java 8中的两个重要特性:Lambda表达式和Stream API。Lambda表达式是一种新的编程语法,它允许我们将函数作为参数传递给其他方法,从而使代码更加简洁。Stream API是一种用于处理集合的新工具,它提供了一种高效且易于使用的方式来处理数据。通过结合使用这两个特性,我们可以编写出更加简洁、高效的Java代码。
7 0
|
1天前
|
存储 安全 Java
Java中的这些String特性可能需要了解下
Java中的String特性你知道哪些?虽然String很常见,通过源码可以看到String的值传递、字符串表和不可变性。本文基于JDK17说明。
9 1
|
1天前
|
存储 Java
Java基础复习(DayThree):字符串基础与StringBuffer、StringBuilder源码研究
Java基础复习(DayThree):字符串基础与StringBuffer、StringBuilder源码研究
Java基础复习(DayThree):字符串基础与StringBuffer、StringBuilder源码研究
|
2天前
|
存储 安全 Java
Java 18新特性
【5月更文挑战第16天】Java 18于2022年3月发布,包含多项新特性和改进,如文件系统链接、文本块、表达式求值API、`ForkJoinPool`优化、`Optional`新方法等。亮点还包括预览特性:Record Pattern Matching for Switch和增强的开关表达式。此外,还有日期时间API扩展、Vector API的进一步孵化、默认UTF-8字符集的研究以及对Security Manager的弃用等。这些更新旨在提升开发效率、性能和安全性。
14 0
|
3天前
|
Java
Java String 避免空指针的方法
Java String 避免空指针的方法
5 0
|
3天前
|
Java API
Java 8新特性之Lambda表达式与Stream API实践指南
【5月更文挑战第15天】 随着Java语言的不断发展,Java 8作为一个重要的版本,引入了许多令人兴奋的新特性。其中,Lambda表达式和Stream API是Java 8最受关注的两个特性。本文将深入探讨Lambda表达式的基本概念、语法和使用场景,以及如何结合Stream API实现更加简洁、高效的代码编写。通过实例演示,帮助读者快速掌握这两个新特性,提高Java编程能力。
|
3天前
|
Java 程序员 API
Java 8新特性之Lambda表达式与Stream API的深度解析
【5月更文挑战第12天】本文将深入探讨Java 8中的两个重要新特性:Lambda表达式和Stream API。我们将从基本概念入手,逐步深入到实际应用场景,帮助读者更好地理解和掌握这两个新特性,提高Java编程效率。
42 2
|
4天前
|
Java 编译器 开发者
Java一分钟之-继承:复用与扩展类的特性
【5月更文挑战第9天】本文探讨了Java中的继承机制,通过实例展示了如何使用`extends`创建子类继承父类的属性和方法。文章列举了常见问题和易错点,如构造器调用、方法覆盖、访问权限和类型转换,并提供了解决方案。建议深入理解继承原理,谨慎设计类结构,利用抽象类和接口以提高代码复用和扩展性。正确应用继承能构建更清晰、灵活的代码结构,提升面向对象设计能力。
17 0