Java SE 基础知识(2)--- String 的构造方法

String 对于所有 Java 程序员来说都不会陌生,几乎每天甚至每个程序都会和 String 打交道,因此将 String 的常用知识汇集在此,方便查阅。

概叙:

Java 中是如此定义 String 的:

public final class String extends Object implements Serializable, Comparable<String>, CharSequence

String 是 final 类型的,继续看下面的解释:

The String class represents character strings.

All string literals in Java programs, such as "abc", are implemented as instances of this class.

Strings are constant; their values cannot be changed after they are created.

String 对象代表了字符的串或序列,Java 中所有字面量的字符串都是 String 的对象;

String 是常量,它的值一旦被创建就不能改变了。

String buffers support mutable strings. Because String objects are immutable they can be shared.

接下来说字符缓冲区支持可变的字符串,因为缓冲区里面的字符串对象们可以被共享(其实就是使对象的引用发生了改变)。

在 Java 中,提供了通过字符串连接符( + )号,将其他类型的对象转换成 String 类型:

The Java language provides special support for the string concatenation operator ( + ), and for conversion of other objects to strings. String concatenation is implemented through the StringBuilder(or StringBuffer) class and its append method. String conversions are implemented through the method toString, defined by Object and inherited by all classes in Java.

int i = 123;String str2 = i + "abc";
/**
* 上面一句生成的 class 文件如下:
* String str2 = (new StringBuilder(String.valueOf(i))).append("abc").toString();
* String 对 “+” 的支持使用了 StringBuilder 以及它的 append 和 toString 方法。
*/

表面看似简单,其实运算复杂,不如直接用 String.valueOf 来的快:

int i = 1;
String strNew = String.valueOf(1) + "abc";

构造方法:

1)无参构造方法

String()
Initializes a newly created String object so that it represents an empty character sequence.

该构造方法会创建空的字符序列,注意这个构造方法的使用,因为创造不必要的字符串对象是不可变的。因此不建议采取下面的创建 String 对象:

String str = new String()
str = "sample";

这样的结果可想而知,产生了不必要的对象。

2)参数为字符串类型

String(String original)
Initializes a newly created String object so that it represents the same sequence of characters as the argument; in other words, the newly created string is a copy of the argument string.

源 String 的值不会影响目标 String 的值,但是用到比较少,或许结合 subString 方法使用:

String original = "1234567890";
String str = new String(original.subString(2, 5));

这样写是有必要的,当 original 是个大字符串时,这种截取方法可以使得新的字符串对象指向新的对象,而不是原来的 original,减少内存占用。

3)参数为 byte 数组类型

String(byte[] bytes)
Constructs a new String by decoding the specified array of bytes using the platform‘s default charset.

String(byte[] bytes, Charset charset)
Constructs a new String by decoding the specified array of bytes using the specified charset.

byte 是网络传输或存储的序列化形式,所以在很多传输和存储的过程中需要将 byte[] 数组和 String 进行相互转化。

有关 IO 流的代码中会出现这个构造方法,字符编码导致的乱码问题也是比较多的,这里需要注意:一旦看到 byte 数组,一定要想到编码问题。

经常会用到 getBytes(Charset charset) 方法:

try {
  byte[] byteArr = strNew.getBytes("UTF-8");
  String newString = new String(byteArr, "UTF-8");
} catch (UnsupportedEncodingException e) {
  e.printStackTrace();
}

4)参数为 char 数组类型

String(char[] value)
Allocates a new String so that it represents the sequence of characters currently contained in the character array argument.

这里值得注意的是:当我们使用字符数组创建 String 的时候,会用到 Arrays.copyOf 方法或 Arrays.copyOfRange 方法。这两个方法是将原有的字符数组中的内容逐一的复制到 String 中的字符数组中。会创建一个新的字符串对象,随后修改的字符数组不影响新创建的字符串。

public String(char value[]) {
  this.value = Arrays.copyOf(value, value.length);
}

5)参数为 StringBuilder 或者 StringBuffer 类型

String(StringBuffer buffer)
Allocates a new string that contains the sequence of characters currently contained in the string buffer argument.
String(StringBuilder builder)
Allocates a new string that contains the sequence of characters currently contained in the string builder argument.

个人认为这种方式的构造方法用的比较少吧,如果是这两种类型的,用 toString 方法的更方便一些。

StringBuilder sbb = new StringBuilder();
sbb.append("hello ").append("world");
String str1 = sbb.toString();

特别感谢以下博文:

Java 源码分析 —— String 的设计

Java 中 String 与 byte[] 的转换

时间: 2024-12-23 12:04:04

Java SE 基础知识(2)--- String 的构造方法的相关文章

Java SE 基础知识(String,Array)

String 类: 1. 对于String对象的相等性判断来说,请使用equals()方法,而不是==.String的equals()是判断当前字符串与传进来的字符串的内容是否一致. 2. String是常量,其对象一旦创建完毕就无法改变.当使用+拼接字符串时,会生成新的String对象,而不是向原有的String对象追加内容. 3. String Pool (字符串池) 在栈内存中. 4. String s = “aaa”;(采用字面值方式赋值) 1). 查找 String Pool 中是否存

Java SE 基础知识(1)

常量: 常量是一种标识符,它的值在运行期间恒定不变,并且常量在程序中只能被引用,而不能被重新赋值. 常量的命名规则: 1.在 Java 中,在变量声明中加入 final 关键字代表常量,加入 static 关键字代表类变量.一般结合起来声明一个变量: 2.尽量使用含义直观的常量来表示那些将在程序中多次出现的数字或字符串: public static final double PI = 3.1415926; 在 Java 接口中声明一个变量,编译时会自动加上 public static final

Java SE 基础知识(二)

1. 类由两大部分构成:属性和方法.属性一般用名词来表示,方法一般用动词来表示. 2. 如果一个java源文件中定义了多个类,那么这些类中最多只能有一个类是public的,可以都不是public的. 3. 在Java中进行方法参数传递时,无论传递的是原生数据类型还是引用数据类型,参数传递方式统一是传值(pass by value),Java中没有传递引用(pass by reference)的概念. 4. 方法重载(Overload):表示两个或多个方法名字相同,但方法参数不同.方法参数不同有两

什么才是java的基础知识?

近日里,很多人邀请我回答各种j2ee开发的初级问题,我无一都强调java初学者要先扎实自己的基础知识,那什么才是java的基础知识?又怎么样才算掌握了java的基础知识呢?这个问题还真值得仔细思考. 我做j2ee开发已经超过十载,作为过来人,心路历程估计和大家差不多.编码的前几年,很长一段时间觉得java简单,开发实现各种功能都很轻松,代码写起来根本不费劲(主要是因为写的代码都是一些功能业务逻辑).但同时自己心里明白,自己其实没有什么水平,自己这3,4年以来学懂的东西就那么多,其他人几个月就可以

黑马程序员——Java集合基础知识之Map

Map概念 要同时存储两个元素Key和Value,他们之间有映射关系,每个键不能重复,每个键只能映射到一个值. 当数据之间存在映射关系的时候,考虑使用Map集合. Map常用方法 如果添加的键原来有值,后添加的值会覆盖前面的值,并返回之前的值.put会返回来先添加的值,后添加的值会覆盖原有的值. Map tm =new TreeMap(); tm.put (key, value);//MAP没有add tm.remove (key) ;//去除一个key和对应的value,若不存在key返回nu

黑马程序员——Java集合基础知识之Collection

集合基础知识--Collection Java中集合框架由常用的Collection接口和Map接口组成,而Collection接口又有两个子接口,是List接口和Set接口,常用的集合框架由这三个类组成. List接口的功能方法 List的使用最为简单,创建集合,通过add方法添加元素,get方法获取元素,通过迭代器获取元素.List接口存放的数据无序的,添加速度快,但是查询速度慢,因为查询的时候必须遍历,每次都重头开始,效率较低.常用实现类有ArrayList,LinkedList. Lis

java多线程基础知识

1.ThrTest.java 继承Thread类方式 public class ThrTest extends Thread { private String name; public ThrTest() { } public ThrTest(String name) { this.name = name; } public void run() { for (int i = 0; i < 5; i++) { System.out.println(name + "运行 " + i

黑马程序员——java多线程基础知识1

多线程 进程是一个正在执行的程序. cpu在同时执行这些程序,其实是跳跃式的,做快速的切换,时间很短.一个进程可能存在多条路径.迅雷的多路径.每一个进行执行都有一个执行顺序,该顺序是一个执行路径,或这叫一个控制单元.每一个进程至少有一个线程,线程就是进程中的一个独立的控制单元,线程控制进程的执行.jvm启动的时候会有一个进程就叫做java,exe,该进程中至少有一个线程在控制Java程序的执行 ,而且该线程的执行代码在 主函数中.该线程称为主线程.虚拟机至少也有两个线程,一个主线程执行,另一个负

黑马程序员——Java多线程基础知识2

多线程协同 线程间的通讯:我们对资源的操作动作不同,比如说两个卡车一个拉煤一个装煤.但是他们共享了一个资源. 怎么样把这个资源拿出来?怎样把车装满?这个资源当然是一个类,他里面的组成元素就是对象!!现在我们就要有操作对象的思想了,我用对象把这车装满,现在一车装一个对象. 等待唤醒机制: 用的不是sleep是wait.flag标记,这是两人沟通的方式.其实每个标记就要做一次等待或者notify,判断wait,改值notify.线程池.notify唤醒里面的线程,按顺序唤醒.wait和notify必