前言之前我们经常通过StringBuffer或者StingBuilder来拼接字符串,但是你知道Java8中引入的StringJoiner吗?它比前者更优雅、更灵活。如果你还在使用StringBuffer拼接,强烈建议你试试StringJoiner。简介在实际的StringJoiner类之前,如果我们希望最后的一串数据用逗号分隔,大概是这样的StringBuildersb=newStringBuilder();IntStream.range(1,10).forEach(i->{sb.append(i+"");if(i<10){sb.append(",")}});如果引入了StringJoiner,如何处理?StringJoinersj=newStringJoiner(",");IntStream.range(1,10).forEach(i->sj.add(i+""));是不是更简单直观?另外,StringJoiner类的构造函数还可以有选择地从我们自定义的前缀开始,以自定义的后缀结束,更加灵活实用。//取值为分隔符、前缀、后缀println(stringJoiner.toString());输出结果:[xiao,zhi]StringJoiner在处理sql拼接的时候也很方便,比如条件拼接sql的时候:StringJoinerjoiner3=newStringJoiner("','","'","'");joiner3.add("1").add("2");//Output:'1','2'更多实用功能,大家自行探索。源码该类的源码非常简单,大家也能轻松看懂。StringJoiner更像是一种装饰器模式,将StringBuilder隐藏在外面。不过需要注意的是,StringJoiner并不处理一些基本的集合元素,比如添加到列表中的元素,更多是为Collectors设计的。包java.util;publicfinalclassStringJoiner{privatefinalStringprefix;//前缀privatefinalStringdelimiter;//间隔符privatefinalStringsuffix;//后缀privateStringBuildervalue;//值privateStringemptyValue;//空值publicStringJoiner(CharSequencedelimiter){this(delimiter,"","");//默认前缀和suffixis"",重载调用}publicStringJoiner(CharSequencedelimiter,CharSequenceprefix,CharSequencesuffix){//空格,前缀和后缀判断是否为null,null会抛出异常Objects.requireNonNull(prefix,"Theprefixmustnotbenull");Objects.requireNonNull(delimiter,"Thedelimitermustnotbenull");Objects.requireNonNull(suffix,"Thesuffixmustnotbenull");//成员变量赋值this.prefix=prefix.toString();this.delimiter=delimiter.toString();this.suffix=suffix.toString();thisthis.emptyValue=this.prefix+this.suffix;//空值设置为只有前缀和后缀}//设置空值,检查是否为nullpublicStringJoinersetEmptyValue(CharSequenceemptyValue){this.emptyValue=Objects.requireNonNull(emptyValue,"Theemptyvaluemustnotbenull").toString();返回nthis;}@OverridepublicStringtoString(){if(value==null){returnemptyValue;//如果没有值,则返回空值或后续的空值}else{if(suffix.equals("")){returnvalue.toString();//后缀为“””,直接返回字符串,不加}else{//后缀不是“”,加后缀,然后直接返回字符串,修改长度ininitialLength=value.length();Stringresult=value.append(suffix).toString();//resetvaluetopre-appendinitialLengthvalue.setLength(initialLength);returnresult;}}}//初始化,先加前缀,再加每次一个spacer,StringBuilder后续appendstringpublicStringJoineradd(CharSequencenewElement){prepareBuilder().append(newElement);returnthis;}//合并StringJoiner,注意后面不需要StringJoiner的前缀,后面的appen在publicStringJoinermerge(StringJoinerother){Objects.requireNonNull(other);if(other.value!=null){finalintlength=other.value.length();//lockthelengthsothatwecanseizethedatatobeappended//beforeinitiatecopyingtoavoidinterference,especiallywhen//merge'this'StringBuilderbuilder=prepareBuilder();builder.append(other.value,other.prefix.length(),length);}returnthis;}//初始化时,先添加前缀,每次添加后添加间隔符privateStringBuilderprepareBuilder(){if(value!=null){value.append(delimiter);}else{value=newStringBuilder().append(prefix);}returnvalue;}publicintlength(){//Rememberthatweneveractuallyappendthesuffixunlesswereturn//thefull(present)valueorsomesub-stringorlengthofit,sothat//wecanaddonmoreifweneedto.//添加后缩的长度return(value!=null?value.length()+suffix.length():emptyValue.length());}}
