当前位置:网站首页>StringJoiner详解
StringJoiner详解
2022-07-31 02:13:00 【likelong965】
一、什么是StringJoiner
StringJoiner是Java 8新增的一个API,他是基于StringBuilder实现,用于实现对字符串之间通过分隔符拼接的场景。
有些字符串拼接场景,使用StringBuilder或StringBuffer会显得比较繁琐。
如以下字符串:
(hello, guys, 欢迎大家)
这种字符串有前缀后缀并且由 “,” 分隔的字符串,在 Java 8 之前要使用 StringBuilder/ StringBuffer 进行拼接,如下:
StringBuilder sb = new StringBuilder();
sb.append("(");
sb.append("hello");
sb.append(",");
sb.append("guys");
sb.append(",");
sb.append("欢迎大家");
sb.append(")");
String str = sb.toString();
上述代码显得十分难看又略显繁琐。
二、StringJoiner基本使用
(hello, guys, 欢迎大家)
Java 8使用StringJonier来实现,如下:
StringJoiner stringJoiner = new StringJoiner(",", "(", ")");
stringJoiner.add("hello");
stringJoiner.add("guys");
stringJoiner.add("欢迎大家");
StringJonier实现就显得比较优雅!
三、StringJoiner详细介绍
StringJoiner 的类结构图:
3.1、成员变量
- prefix:拼接后的字符串前缀
- delimiter:拼接时的字符串分隔符
- suffix:拼接后的字符串后缀
- value:拼接后的值
- emptyValue:空值的情况,
value为 null 时返回
3.2、构造方法
StringJoiner有两个构造方法
一个是要求传入分隔符、前缀和后缀
另一个是只需要传入分隔符(前缀和后缀默认是"")
源码如下:
public StringJoiner(CharSequence delimiter) {
this(delimiter, "", "");
}
public StringJoiner(CharSequence delimiter,
CharSequence prefix,
CharSequence suffix) {
Objects.requireNonNull(prefix, "The prefix must not be null");
Objects.requireNonNull(delimiter, "The delimiter must not be null");
Objects.requireNonNull(suffix, "The suffix must not be null");
// make defensive copies of arguments
this.prefix = prefix.toString();
this.delimiter = delimiter.toString();
this.suffix = suffix.toString();
this.emptyValue = this.prefix + this.suffix;
}
可以看到 emptyValue
默认为前缀+后缀组成。
3.3、公开方法
- setEmptyValue:设置空值
- toString:转换成 String
- add:添加字符串
- merge:从另一个 StringJoiner 合并
- length:长度(包括前缀后缀)
主要看add()源码:
public StringJoiner add(CharSequence newElement) {
prepareBuilder().append(newElement);
return this;
}
private StringBuilder prepareBuilder() {
if (value != null) {
value.append(delimiter);
} else {
value = new StringBuilder().append(prefix);
}
return value;
}
toString()源码
public String toString() {
if (value == null) {
return emptyValue;
} else {
if (suffix.equals("")) {
return value.toString();
} else {
int initialLength = value.length();
String result = value.append(suffix).toString();
// reset value to pre-append initialLength
value.setLength(initialLength);
return result;
}
}
}
可以看到内部其实就是用的StringBuilder进行封装的,首次创建会先拼接前缀,后续先添加分隔符,再添加字符串。
主要就通过上述两个方法,实现前缀、后缀以及分隔符的拼接。(最后输出才进行后缀的拼接)
另外一点,add 方法就是返回 StringJoiner 本身,所以可以像StringBuilder/ StringBuffer 一样进行流式处理。如下:
StringJoiner stringJoiner = new StringJoiner(",", "(", ")").add("hello").add("guys").add("欢迎大家");
System.out.println(stringJoiner);
3.4、空值处理
没有拼接任何字符串的几个空值处理场景。
3.4.1、输出空白字符串
StringJoiner stringJoiner = new StringJoiner(",");
System.out.println(stringJoiner.toString());
3.4.2、输出前后缀
StringJoiner stringJoiner = new StringJoiner(",", "[", "]");
System.out.println(stringJoiner.toString());
输出:[]
3.4.3、输出指定字符串
StringJoiner stringJoiner = new StringJoiner(",", "[", "]");
stringJoiner.setEmptyValue("likelong");
System.out.println(stringJoiner.toString());
输出:likelong
上面三个小案例都可以在源码中找到答案。
四、String.join()
String.join() 这是针对 StringJoiner 又封装了一层的 API,同样出自 Java 8,可以传入动态参数或者迭代器。
- java.lang.String#join(java.lang.CharSequence, java.lang.CharSequence…)
- java.lang.String#join(java.lang.CharSequence, java.lang.Iterable<? extends java.lang.CharSequence>)
源码:
public static String join(CharSequence delimiter, CharSequence... elements) {
Objects.requireNonNull(delimiter);
Objects.requireNonNull(elements);
// Number of elements not likely worth Arrays.stream overhead.
StringJoiner joiner = new StringJoiner(delimiter);
for (CharSequence cs: elements) {
joiner.add(cs);
}
return joiner.toString();
}
public static String join(CharSequence delimiter,
Iterable<? extends CharSequence> elements) {
Objects.requireNonNull(delimiter);
Objects.requireNonNull(elements);
StringJoiner joiner = new StringJoiner(delimiter);
for (CharSequence cs: elements) {
joiner.add(cs);
}
return joiner.toString();
}
由源码可以看出,该方法只能进行分隔符拼接,并不能拼接前缀和后缀。
实际操作:
String join = String.join(",", "hello", "world", "likelong");
System.out.println(join);
输出:hello,world,likelong
五、Collectors.joining(“,”)
Collectors.joining(“,”)底层也是通过StringJoiner实现的。源码如下:
public static Collector<CharSequence, ?, String> joining(CharSequence delimiter) {
return joining(delimiter, "", "");
}
/** * Returns a {@code Collector} that concatenates the input elements, * separated by the specified delimiter, with the specified prefix and * suffix, in encounter order. * * @param delimiter the delimiter to be used between each element * @param prefix the sequence of characters to be used at the beginning * of the joined result * @param suffix the sequence of characters to be used at the end * of the joined result * @return A {@code Collector} which concatenates CharSequence elements, * separated by the specified delimiter, in encounter order */
public static Collector<CharSequence, ?, String> joining(CharSequence delimiter,
CharSequence prefix,
CharSequence suffix) {
return new CollectorImpl<>(
() -> new StringJoiner(delimiter, prefix, suffix),
StringJoiner::add, StringJoiner::merge,
StringJoiner::toString, CH_NOID);
}
针对不同的场景使用不同的 API,这才是最佳最优雅的处理方式,不要只会使用 StringBuilder!
边栏推荐
- Can an inexperienced college graduate switch to software testing?my real case
- 力扣刷题之有效的正方形(每日一题7/29)
- uniapp使用第三方字体
- 最大路径和
- What are the project management tools like MS Project
- Fiddler抓包模拟弱网络环境测试
- tcp框架需要解决的问题
- 静态路由+PAT+静态NAT(讲解+实验)
- Software Testing Defect Reporting - Definition, Composition, Defect Lifecycle, Defect Tracking Post-Production Process, Defect Tracking Process, Purpose of Defect Tracking, Defect Management Tools
- PDF 拆分/合并
猜你喜欢
After reading "MySQL Database Advanced Practice" (SQL Xiao Xuzhu)
【Bank Series Phase 1】People's Bank of China
汉诺塔问题
STP选举(步骤+案列)详解
STM32CUBEMX开发GD32F303(11)----ADC在DMA模式下扫描多个通道
Path and the largest
MySql installation and configuration super detailed tutorial and simple method of building database and table
真正的CTO,是一个懂产品的技术人
ShardingJDBC基本介绍
Intranet Infiltration - Privilege Escalation
随机推荐
mysql 索引
Introduction to flask series 】 【 flask - using SQLAlchemy
Project development software directory structure specification
[1154]如何将字符串转换为datetime
ShardingJDBC使用总结
力扣刷题之爬楼梯(7/30)
FPGA-based vending machine
PDF 拆分/合并
Path and the largest
医疗影像领域AI软件开发流程
MPPT solar charge controller data collection - through the gateway acquisition capacity battery SOC battery voltage, wi-fi
【银行系列第一期】中国人民银行
系统需求多变如何设计
There is a problem with the multiplayer-hlap package and the solution cannot be upgraded
cudaMemcpy学习笔记
Inner monologue from a female test engineer...
MySQL stored procedure
tcp框架需要解决的问题
Drools规则属性,高级语法
成为比开发硬气的测试人,我都经历了什么?