Java 앱에서 작업하는 동안 최근에 쉼표로 구분 된 값 목록을 어셈블하여 얼마나 많은 요소가 사전에 있는지 모르면서 다른 웹 서비스에 전달해야했습니다. 내가 머리 꼭대기에서 내릴 수있는 최선은 다음과 같습니다.
public String appendWithDelimiter( String original, String addition, String delimiter ) {
if ( original.equals( "" ) ) {
return addition;
} else {
return original + delimiter + addition;
}
}
String parameterString = "";
if ( condition ) parameterString = appendWithDelimiter( parameterString, "elementName", "," );
if ( anotherCondition ) parameterString = appendWithDelimiter( parameterString, "anotherElementName", "," );
나는 모든 곳에서 문자열이 생성되기 때문에 이것이 효율적이지 않다는 것을 알고 있지만 최적화보다 명확성을 추구했습니다.
루비에서는 대신 다음과 같이 할 수 있습니다.
parameterArray = [];
parameterArray << "elementName" if condition;
parameterArray << "anotherElementName" if anotherCondition;
parameterString = parameterArray.join(",");
그러나 Java에는 join 명령이 없기 때문에 동등한 것을 알아낼 수 없었습니다.
Java에서 이것을 수행하는 가장 좋은 방법은 무엇입니까?
답변
프리 자바 8 :
Apache의 commons lang은 여기에 당신의 친구입니다-그것은 당신이 Ruby에서 참조하는 것과 매우 유사한 join 메소드를 제공합니다 :
StringUtils.join(java.lang.Iterable,char)
자바 8 :
자바 (8)을 통해 밖으로 상자의 결합을 제공 StringJoiner
하고 String.join()
. 아래 스 니펫은 사용 방법을 보여줍니다.
StringJoiner joiner = new StringJoiner(",");
joiner.add("01").add("02").add("03");
String joinedString = joiner.toString(); // "01,02,03"
String.join(CharSequence delimiter, CharSequence... elements))
String joinedString = String.join(" - ", "04", "05", "06"); // "04 - 05 - 06"
String.join(CharSequence delimiter, Iterable<? extends CharSequence> elements)
List<String> strings = new LinkedList<>();
strings.add("Java");strings.add("is");
strings.add("cool");
String message = String.join(" ", strings);
//message returned is: "Java is cool"
답변
java.util.Lists에서 작동하는 작은 결합 스타일 유틸리티 메소드를 작성할 수 있습니다.
public static String join(List<String> list, String delim) {
StringBuilder sb = new StringBuilder();
String loopDelim = "";
for(String s : list) {
sb.append(loopDelim);
sb.append(s);
loopDelim = delim;
}
return sb.toString();
}
그런 다음 다음과 같이 사용하십시오.
List<String> list = new ArrayList<String>();
if( condition ) list.add("elementName");
if( anotherCondition ) list.add("anotherElementName");
join(list, ",");
답변
안드로이드의 경우, Commons의 StringUtils 클래스를 사용할 수 없으므로 이것을 사용했습니다.
android.text.TextUtils.join(CharSequence delimiter, Iterable tokens)
http://developer.android.com/reference/android/text/TextUtils.html
답변
구글의 구아바 라이브러리 가 com.google.common.base.Joiner의 같은 작업을 해결하는 데 도움이 클래스를.
샘플:
"My pets are: " + Joiner.on(", ").join(Arrays.asList("rabbit", "parrot", "dog"));
// returns "My pets are: rabbit, parrot, dog"
Joiner.on(" AND ").join(Arrays.asList("field1=1" , "field2=2", "field3=3"));
// returns "field1=1 AND field2=2 AND field3=3"
Joiner.on(",").skipNulls().join(Arrays.asList("London", "Moscow", null, "New York", null, "Paris"));
// returns "London,Moscow,New York,Paris"
Joiner.on(", ").useForNull("Team held a draw").join(Arrays.asList("FC Barcelona", "FC Bayern", null, null, "Chelsea FC", "AC Milan"));
// returns "FC Barcelona, FC Bayern, Team held a draw, Team held a draw, Chelsea FC, AC Milan"
다음은 구아바의 문자열 유틸리티에 대한 기사 입니다.
답변
Java 8에서는 다음을 사용할 수 있습니다 String.join()
.
List<String> list = Arrays.asList("foo", "bar", "baz");
String joined = String.join(" and ", list); // "foo and bar and baz"
또한 Stream API 예제에 대한 이 답변 을 살펴보십시오 .
답변
당신은 그것을 일반화 할 수 있지만 잘 말한 것처럼 Java에는 참여하지 않습니다.
이것은 더 잘 작동 할 수 있습니다.
public static String join(Iterable<? extends CharSequence> s, String delimiter) {
Iterator<? extends CharSequence> iter = s.iterator();
if (!iter.hasNext()) return "";
StringBuilder buffer = new StringBuilder(iter.next());
while (iter.hasNext()) buffer.append(delimiter).append(iter.next());
return buffer.toString();
}
답변
Java 8에서는 다음과 같이 할 수 있습니다.
list.stream().map(Object::toString)
.collect(Collectors.joining(delimiter));
list에 null이 있으면 다음을 사용할 수 있습니다.
list.stream().map(String::valueOf)
.collect(Collectors.joining(delimiter))
또한 접두사와 접미사를 지원합니다.
list.stream().map(String::valueOf)
.collect(Collectors.joining(delimiter, prefix, suffix));