Мені потрібно розділити String на масив одиночних символів Strings.
Наприклад, розщеплення "кота" дасть масив "c", "a", "t"
.split("")
зробить це.
Мені потрібно розділити String на масив одиночних символів Strings.
Наприклад, розщеплення "кота" дасть масив "c", "a", "t"
.split("")
зробить це.
Відповіді:
"cat".split("(?!^)")
Це призведе
масив ["c", "a", "t"]
(?!
... )
- синтаксис регулярного вираження для негативного твердження - він стверджує, що немає відповідності тому, що знаходиться всередині нього. І ^
відповідає початку рядка, тому регулярний вираз відповідає всій позиції, яка не є початком рядка, і вставляє там розкол. Цей регулярний вираз також збігається в кінці рядка і тому також додає порожній рядок до результату, за винятком того, що в String.split
документації написано, що "остаточні порожні рядки не включаються в результуючий масив".
String.split
злегка змінилася, так що провідні порожні рядки, що виробляються збігом нульової ширини, також не включаються в масив результатів, тому (?!^)
твердження про те, що позиція не є початком рядка, стає непотрібним, дозволяючи регулярному вираженню бути спрощеним до нічого - "cat".split("")
- але в Java 7 і нижче, що створює провідну порожню рядок у масиві результатів.
"cat".toCharArray()
Але якщо вам потрібні струни
"cat".split("")
Редагувати: що поверне порожнє перше значення.
.toCharArray()
все одно користуєтеся ; він уникає регулярного вираження та повертає масив char
примітивів, тому він швидший і легший. Дивно, що вам потрібен масив з 1 символьних рядків .
String str = "cat";
char[] cArray = str.toCharArray();
cArray
назад String
?
Якщо символи, що знаходяться за межами базової багатомовної площини , очікуються на вході (деякі символи CJK, нові емоджи ...), такі підходи "a💫b".split("(?!^)")
використовувати не можна, оскільки вони розбивають такі символи (результати array ["a", "?", "?", "b"]
) і потрібно використовувати щось безпечніше:
"a💫b".codePoints()
.mapToObj(cp -> new String(Character.toChars(cp)))
.toArray(size -> new String[size]);
Ефективним способом перетворення рядка в масив одно символьних рядків було б це зробити:
String[] res = new String[str.length()];
for (int i = 0; i < str.length(); i++) {
res[i] = Character.toString(str.charAt(i));
}
Однак це не враховує того факту, що char
в a String
може насправді представляти половину кодової точки Unicode. (Якщо точка коду відсутня в BMP.) Щоб вирішити це, вам потрібно перебрати кодові точки ... що складніше.
Цей підхід буде швидшим, ніж використання String.split(/* clever regex*/)
, і, ймовірно, буде швидшим, ніж використання потоків Java 8+. Це швидше, ніж це:
String[] res = new String[str.length()];
int 0 = 0;
for (char ch: str.toCharArray[]) {
res[i++] = Character.toString(ch);
}
тому що toCharArray
має скопіювати символів у новий масив.
Можливо, ви можете використовувати цикл for, який проходить через вміст String і витягує символи за символами, використовуючи charAt
метод.
У поєднанні з, ArrayList<String>
наприклад, ви можете отримати масив окремих символів.
Якщо початковий рядок містить додаткові символи Unicode , він split()
не працює, оскільки він розбиває цих символів на сурогатні пари. Щоб правильно поводитися з цими спеціальними символами, працює такий код:
String[] chars = new String[stringToSplit.codePointCount(0, stringToSplit.length())];
for (int i = 0, j = 0; i < stringToSplit.length(); j++) {
int cp = stringToSplit.codePointAt(i);
char c[] = Character.toChars(cp);
chars[j] = new String(c);
i += Character.charCount(cp);
}
Оператор розповсюдження [ ...
] створює масив з кожним символом у рядку:
const cat= 'cat';
const arrayized = [...cat] // ['c', 'a', 't'];
console.log(arrayized);