Java-эквивалент PHP implode (',', array filter (array ())
Я часто использую этот кусок кода в PHP
$ordine['address'] = implode(', ', array_filter(array($cliente['cap'], $cliente['citta'] ,$cliente['provincia'])));
Он очищает пустые строки и присоединяет их к ",". Если остается только один, он не добавляет лишнюю ненужную запятую. Он не добавляет запятую в конце. Если никто не остается, он возвращает пустую строку.
таким образом, я могу получить один из следующих результатов
""
"Street abc 14"
"Street abc 14, 00168"
"Street abc 14, 00168, Rome"
какая лучшая реализация Java (меньше кода) в Java без необходимости добавлять внешние библиотеки (разработка для Android) ?
9 ответов:
обновленная версия с использованием Java 8 (Оригинал в конце поста)
Если вам не нужно фильтровать любые элементы, вы можете использовать
строку.join (разделитель CharSequence,
CharSequence...
элементы)
String.join(" > ", new String[]{"foo", "bar"});
String.join(" > ", "foo", "bar");
или строку.join (разделитель CharSequence,
Iterable<? extends CharSequence>
элементы)
String.join(" > ", Arrays.asList("foo", "bar"));
начиная с Java 8, мы можем использовать
StringJoiner
(вместо первоначально использовалисьStringBulder
) и упростить наш код.
Также, чтобы избежать перекомпиляции" *"
regex в каждом вызовеmatches(" *")
мы можем создать отдельный шаблон, который будет содержать его скомпилированную версию в некотором поле и использовать его при необходимости.private static final Pattern SPACES_OR_EMPTY = Pattern.compile(" *"); public static String implode(String separator, String... data) { StringJoiner sb = new StringJoiner(separator); for (String token : data) { if (!SPACES_OR_EMPTY.matcher(token).matches()) { sb.add(token); } } return sb.toString(); }
с потоками наш код можно посмотреть как.
private static final Predicate<String> IS_NOT_SPACES_ONLY = Pattern.compile("^\s*$").asPredicate().negate(); public static String implode(String delimiter, String... data) { return Arrays.stream(data) .filter(IS_NOT_SPACES_ONLY) .collect(Collectors.joining(delimiter)); }
если мы используем потоки, мы можем
filter
элементовPredicate
. В этом случае мы хотим, чтобы предикат принимал строки, которые не являются только пробелами - другими словами, строка должна содержать символ без пробела.мы можем создать такой предикат из рисунка. Предикат, созданный таким образом, будет принимать любые строки, которые будут содержать подстроку, которая может быть сопоставлена регулярным выражением (так что если регулярное выражение будет искать
"\S"
предикат будет принимать строки типа"foo "
," foo bar "
,"whatever"
, а не" "
, ни" "
).так что мы можем использовать
Pattern.compile("\S").asPredicate();
или, возможно, немного более описательный, отрицание строк, которые являются только пробелами или пустыми
Pattern.compile("^\s*$").asPredicate().negate();
далее, когда фильтр удалит все пустые или содержащие только пробелы строки мы можем
collect
остальные элементы. СпасибоCollectors.joining
мы можем решить, какой разделитель использовать.
оригинальный ответ (до Java 8)
public static String implode(String separator, String... data) { StringBuilder sb = new StringBuilder(); for (int i = 0; i < data.length - 1; i++) { //data.length - 1 => to not add separator at the end if (!data[i].matches(" *")) {//empty string are ""; " "; " "; and so on sb.append(data[i]); sb.append(separator); } } sb.append(data[data.length - 1].trim()); return sb.toString(); }
вы можете использовать его как
System.out.println(implode(", ", "ab", " ", "abs"));
или
System.out.println(implode(", ", new String[] { "ab", " ", "abs" }));
выход
ab, abs
вам нужно будет добавить свои строки в ArrayList, удалить пустые и отформатировать их соответственно:
public static String createAddressString( String street, String zip_code, String country) { List<String> list = new ArrayList<String>(); list.add( street); list.add( zip_code); list.add( country); // Remove all empty values list.removeAll(Arrays.asList("", null)); // If this list is empty, it only contained blank values if( list.isEmpty()) { return ""; } // Format the ArrayList as a string, similar to implode StringBuilder builder = new StringBuilder(); builder.append( list.remove(0)); for( String s : list) { builder.append( ", "); builder.append( s); } return builder.toString(); }
кроме того, если у вас
String[]
, массив строк, вы можете легко добавить их в ArrayList:String[] s; List<String> list = new ArrayList<String>( Arrays.asList( s));
вот конкретный ответ Android, который может быть полезен некоторым
String combined = TextUtils.join(",", new String[]{"Red", "Green", "Blue"}); //Result => Red,Green,Blue
обязательно импортируйте класс TextUtils
import android.text.TextUtils;
использование потоков (для java 8 и более поздних версий) было бы альтернативным возможным решением для этого. Вы должны импортировать
java.util.stream.Collectors;
чтобы использовать процесс соединения
Вы можете использовать:
Arrays.asList("foo","bar").stream().collect(Collectors.joining(","));
для достижения желаемого результата.
простой взрыв
public static String implode(String glue, String[] strArray) { String ret = ""; for(int i=0;i<strArray.length;i++) { ret += (i == strArray.length - 1) ? strArray[i] : strArray[i] + glue; } return ret; }
вы можете создавать для него перегрузки..
выше это эквивалент PHP implode.
Вот что вы хотите:import java.lang.* public static String customImplode(String glue, String[] strArray) { String ret = ""; for(int i=0;i<strArray.length;i++) { if (strArray[i].trim() != "") ret += (i == strArray.length - 1) ? strArray[i] : strArray[i] + glue; } return ret; }
вот моя реализация implode:
/** * Implodes the specified items, gluing them using the specified glue replacing nulls with the specified * null placeholder. * @param glue The text to use between the specified items. * @param nullPlaceholder The placeholder to use for items that are <code>null</code> value. * @param items The items to implode. * @return A <code>String</code> containing the items in their order, separated by the specified glue. */ public static final String implode(String glue, String nullPlaceholder, String ... items) { StringBuilder sb = new StringBuilder(); for (String item : items) { if (item != null) { sb.append(item); } else { sb.append(nullPlaceholder); } sb.append(glue); } return sb.delete(sb.length() - glue.length(), sb.length()).toString(); }
public static String implode(List<String> items, String separator) { if (items == null || items.isEmpty()) { return null; } String delimiter = ""; StringBuilder builder = new StringBuilder(); for (String item : items) { builder.append(delimiter).append(item); delimiter = separator; } return builder.toString(); }
используйте эту простую функцию :
private String my_implode(String spacer,String[] in_array){ String res = ""; for(int i = 0 ; i < in_array.length ; i++){ if( !res.equals("") ){ res += spacer; } res += in_array[i]; } return res; }
использование :
data_arr = {"d1","d2","d3"}; your_imploded_text = my_implode(",", data_arr); //output : your_imploded_text = "d1,d2,d3"