Joiner
可連接多個 string,同時避免遇到 null 會發生問題
joiner configuration methods 永遠會回傳新的 Joiner 物件,因此 Joiner 是 thread safe 的
@Test
public void joiner() {
Joiner joiner = Joiner.on("; ").skipNulls();
String joinresult = joiner.join("Harry", null, "Ron", "Hermione");
assertEquals("Harry; Ron; Hermione", joinresult);
Joiner joiner2 = Joiner.on("; ").useForNull("?");
String joinresult2 = joiner2.join("Harry", null, "Ron", "Hermione");
assertEquals("Harry; ?; Ron; Hermione", joinresult2);
String joinresult3 = Joiner.on(",").join(Arrays.asList(1, 5, 7));
assertEquals("1,5,7", joinresult3);
}
Splitter
原本的 String.split 有些奇怪的回傳結果,Splitter提供多個 method,可以自己決定回傳的結果內容。另外 Splitter 可以套用 Pattern, char, Stirng 或 CharMatcher 作為分割標準
Factory method
Method | Description | Example |
---|---|---|
Splitter.on(char) | 以字元分割 | Splitter.on(';') |
Splitter.on(CharMatcher) | 以一組字元分割 | Splitter.on(CharMatcher.BREAKING_WHITESPACE) |
Splitter.on(CharMatcher.anyOf(";,.")) | ||
Splitter.on(String) | 以字串分割 | Splitter.on(", ") |
Splitter.on(Pattern) | 以 regular expression 分割 | Splitter.onPattern("\r?\n") |
Splitter.onPattern(String) | ||
Splitter.fixedLength(int) | 固定長度分割 | Splitter.fixedLength(3) |
Modifier methods
Method | Description | Example | Result |
---|---|---|---|
omitEmptyString() | 忽略 empty string | Splitter.on(',').omitEmptyStrings().split("a,,c,d") | "a", "c", "d" |
trimResults() | 去掉 whitespace | Splitter.on(',').trimResults().split("a, b, c, d") | "a", "b", "c", "d" |
trimResults(CharMatcher) | 去掉一組字元(最前面&最後面) | Splitter.on(',').trimResults(CharMatcher.is('')).split("_a ,_b ,c__") | "a ", "b_ ", "c" |
limit(int) | 最多只分割為 int 個字串後,就不再分割 | Splitter.on(',').limit(3).split("a,b,c,d") | "a", "b", "c,d" |
從 split() 改用 splitToList 會回傳 List
@Test
public void splitter() {
String[] split1 = ",a,,b,".split(",");
// 原生 split 會自動去掉最後一個 ""
// "", "a", "", "b"
assertEquals("[, a, , b]", Arrays.toString(split1));
Iterable<String> split2 =
Splitter.on(',')
.trimResults()
.omitEmptyStrings()
.split("foo,bar,, qux");
// "foo", "bar", "qux"
assertEquals("[foo, bar, qux]", split2.toString());
Iterable<String> split3 = Splitter.on(',').omitEmptyStrings().split("a,,c,d");
// "a", "c", "d"
assertEquals("[a, c, d]", split3.toString());
Iterable<String> split4 = Splitter.on(',').trimResults().split("a, b, c, d");
// "a", "b", "c", "d"
assertEquals("[a, b, c, d]", split4.toString());
Iterable<String> split5 = Splitter.on(',').trimResults(CharMatcher.is('_')).split("_a ,_b_ ,c__");
//"a ", "b_ ", "c"
assertEquals("[a , b_ , c]", split5.toString());
Iterable<String> split6 = Splitter.on(',').limit(3).split("a,b,c,d");
//"a", "b", "c,d"
assertEquals("[a, b, c,d]", split6.toStringa
());
// 改用 splitToList 會回傳 List<String>
List<String> split7 = Splitter.on(',').omitEmptyStrings().splitToList("a,,c,d");
}
How to use Joiner Splitter
Convert List into String Using Joiner
@Test
public void whenConvertListToString_thenConverted() {
List<String> names = Lists.newArrayList("Taipei", "Taichung", "Kaohsiung");
String result = Joiner.on(",").join(names);
assertEquals(result, "Taipei,Taichung,Kaohsiung");
}
Convert Map to String Using Joiner
@Test
public void whenConvertMapToString_thenConverted() {
Map<String, Integer> salary = Maps.newHashMap();
salary.put("Taipei", 1000);
salary.put("Taichung", 1500);
String result = Joiner.on(" , ").withKeyValueSeparator(" = ")
.join(salary);
assertTrue(result.contains("Taipei = 1000"));
assertTrue(result.contains("Taichung = 1500"));
}
Join Nested Collections
@Test
public void whenJoinNestedCollections_thenJoined() {
List<ArrayList<String>> nested = Lists.newArrayList(
Lists.newArrayList("apple", "banana", "orange"),
Lists.newArrayList("cat", "dog", "bird"),
Lists.newArrayList("John", "Jane", "Adam"));
String result = Joiner.on(";").join(Iterables.transform(nested,
new com.google.common.base.Function<List<String>, String>() {
@Override
public String apply(List<String> input) {
return Joiner.on("-").join(input);
}
}));
assertTrue(result.contains("apple-banana-orange"));
assertTrue(result.contains("cat-dog-bird"));
assertTrue(result.contains("John-Jane-Adam"));
}
Handle Null Values While Using Joiner
@Test
public void whenConvertListToStringAndSkipNull_thenConverted() {
List<String> names = Lists.newArrayList("John", null, "Jane", "Adam", "Tom");
String result = Joiner.on(",").skipNulls().join(names);
assertEquals(result, "John,Jane,Adam,Tom");
}
@Test
public void whenUseForNull_thenUsed() {
List<String> names = Lists.newArrayList("John", null, "Jane", "Adam", "Tom");
String result = Joiner.on(",").useForNull("nameless").join(names);
assertEquals(result, "John,nameless,Jane,Adam,Tom");
}
Create Map From String Using Splitter
@Test
public void whenCreateMapFromString_thenCreated() {
String input = "John=first,Adam=second";
Map<String, String> result = Splitter.on(",")
.withKeyValueSeparator("=")
.split(input);
assertEquals("first", result.get("John"));
assertEquals("second", result.get("Adam"));
}
Split String With Multiple Separators
@Test
public void whenSplitStringOnMultipleSeparator_thenSplit() {
String input = "apple.banana,,orange,,.";
List<String> result = Splitter.onPattern("[.,]")
.omitEmptyStrings()
.splitToList(input);
assertTrue(result.contains("apple"));
assertTrue(result.contains("banana"));
assertTrue(result.contains("orange"));
}
Split a String at Specific Length
@Test
public void whenSplitStringOnSpecificLength_thenSplit() {
String input = "Hello world";
List<String> result = Splitter.fixedLength(3).splitToList(input);
//Hel", "lo ", "wor", "ld"
assertEquals("[Hel, lo , wor, ld]", result.toString());
}
Limit the Split Result
@Test
public void whenLimitSplitting_thenLimited() {
String input = "a,b,c,d,e";
List<String> result = Splitter.on(",")
.limit(4)
.splitToList(input);
assertEquals(4, result.size());
// ["a", "b", "c", "d,e"]
assertEquals("[a, b, c, d,e]", result.toString());
}