Created
September 18, 2016 02:32
-
-
Save pygman/54f8e9a3906fc1410c6a42eed3db6eca to your computer and use it in GitHub Desktop.
Strman Java字符串处理库 学习
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* | |
* | |
* * The MIT License | |
* * | |
* * Copyright 2016 Shekhar Gulati <[email protected]>. | |
* * | |
* * Permission is hereby granted, free of charge, to any person obtaining a copy | |
* * of this software and associated documentation files (the "Software"), to deal | |
* * in the Software without restriction, including without limitation the rights | |
* * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | |
* * copies of the Software, and to permit persons to whom the Software is | |
* * furnished to do so, subject to the following conditions: | |
* * | |
* * The above copyright notice and this permission notice shall be included in | |
* * all copies or substantial portions of the Software. | |
* * | |
* * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | |
* * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | |
* * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | |
* * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | |
* * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | |
* * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN | |
* * THE SOFTWARE. | |
* | |
*/ | |
package strman; | |
import java.util.*; | |
import java.util.function.Predicate; | |
import java.util.function.Supplier; | |
import java.util.regex.Matcher; | |
import java.util.regex.Pattern; | |
import java.util.stream.Stream; | |
import static java.util.stream.Collectors.joining; | |
/** | |
* A String manipulation library without any dependencies | |
*/ | |
public abstract class Strman { | |
private static final Predicate<String> NULL_STRING_PREDICATE = str -> str == null; | |
private static final Supplier<String> NULL_STRING_MSG_SUPPLIER = () -> "'value' should be not null."; | |
private Strman() { | |
} | |
/** | |
* Appends Strings to value | |
* | |
* @param value initial String | |
* @param appends an array of strings to append | |
* @return full String | |
*/ | |
public static String append(final String value, final String... appends) { | |
return appendArray(value, appends); | |
} | |
/** | |
* Append an array of String to value | |
* | |
* @param value initial String | |
* @param appends an array of strings to append | |
* @return full String | |
*/ | |
public static String appendArray(final String value, final String[] appends) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
if (appends == null || appends.length == 0) { | |
return value; | |
} | |
StringJoiner joiner = new StringJoiner(""); | |
for (String append : appends) { | |
joiner.add(append); | |
} | |
return value + joiner.toString(); | |
} | |
/** | |
* Get the character at index. This method will take care of negative indexes. | |
* The valid value of index is between -(length-1) to (length-1). | |
* For values which don't fall under this range Optional.empty will be returned. | |
* | |
* @param value input value | |
* @param index location | |
* @return an Optional String if found else empty | |
*/ | |
public static Optional<String> at(final String value, int index) { | |
if (value == null || value.isEmpty()) { | |
return Optional.empty(); | |
} | |
int length = value.length(); | |
if (index < 0) { | |
index = length + index; | |
} | |
return (index < length && index >= 0) ? Optional.of(String.valueOf(value.charAt(index))) : Optional.empty(); | |
} | |
/** | |
* Returns an array with strings between start and end. | |
* | |
* @param value input | |
* @param start start | |
* @param end end | |
* @return Array containing different parts between start and end. | |
*/ | |
public static String[] between(final String value, final String start, final String end) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
validate(start, NULL_STRING_PREDICATE, () -> "'start' should be not null."); | |
validate(end, NULL_STRING_PREDICATE, () -> "'end' should be not null."); | |
String[] parts = value.split(end); | |
return Arrays.stream(parts).map(subPart -> subPart.substring(subPart.indexOf(start) + start.length())).toArray(String[]::new); | |
} | |
/** | |
* Returns a String array consisting of the characters in the String. | |
* | |
* @param value input | |
* @return character array | |
*/ | |
public static String[] chars(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return value.split(""); | |
} | |
/** | |
* Replace consecutive whitespace characters with a single space. | |
* | |
* @param value input String | |
* @return collapsed String | |
*/ | |
public static String collapseWhitespace(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return value.trim().replaceAll("\\s\\s+", " "); | |
} | |
/** | |
* Verifies that the needle is contained in the value. The search is case insensitive | |
* | |
* @param value to search | |
* @param needle to find | |
* @return true if found else false. | |
*/ | |
public static boolean contains(final String value, final String needle) { | |
return contains(value, needle, false); | |
} | |
/** | |
* Verifies that the needle is contained in the value. | |
* | |
* @param value to search | |
* @param needle to find | |
* @param caseSensitive true or false | |
* @return true if found else false. | |
*/ | |
public static boolean contains(final String value, final String needle, final boolean caseSensitive) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
if (caseSensitive) { | |
return value.contains(needle); | |
} | |
return value.toLowerCase().contains(needle.toLowerCase()); | |
} | |
/** | |
* Verifies that all needles are contained in value. The search is case insensitive | |
* | |
* @param value input String to search | |
* @param needles needles to find | |
* @return true if all needles are found else false. | |
*/ | |
public static boolean containsAll(final String value, final String[] needles) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return Arrays.stream(needles).allMatch(needle -> contains(value, needle, true)); | |
} | |
/** | |
* Verifies that all needles are contained in value | |
* | |
* @param value input String to search | |
* @param needles needles to find | |
* @param caseSensitive true or false | |
* @return true if all needles are found else false. | |
*/ | |
public static boolean containsAll(final String value, final String[] needles, final boolean caseSensitive) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return Arrays.stream(needles).allMatch(needle -> contains(value, needle, caseSensitive)); | |
} | |
/** | |
* Verifies that one or more of needles are contained in value. This is case insensitive | |
* | |
* @param value input | |
* @param needles needles to search | |
* @return boolean true if any needle is found else false | |
*/ | |
public static boolean containsAny(final String value, final String[] needles) { | |
return containsAny(value, needles, false); | |
} | |
/** | |
* Verifies that one or more of needles are contained in value. | |
* | |
* @param value input | |
* @param needles needles to search | |
* @param caseSensitive true or false | |
* @return boolean true if any needle is found else false | |
*/ | |
public static boolean containsAny(final String value, final String[] needles, final boolean caseSensitive) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return Arrays.stream(needles).anyMatch(needle -> contains(value, needle, caseSensitive)); | |
} | |
/** | |
* Count the number of times substr appears in value | |
* | |
* @param value input | |
* @param subStr to search | |
* @return count of times substring exists | |
*/ | |
public static long countSubstr(final String value, final String subStr) { | |
return countSubstr(value, subStr, true, false); | |
} | |
/** | |
* Count the number of times substr appears in value | |
* | |
* @param value input | |
* @param subStr search string | |
* @param caseSensitive whether search should be case sensitive | |
* @param allowOverlapping boolean to take into account overlapping | |
* @return count of times substring exists | |
*/ | |
public static long countSubstr(final String value, final String subStr, final boolean caseSensitive, boolean allowOverlapping) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return countSubstr(caseSensitive ? value : value.toLowerCase(), caseSensitive ? subStr : subStr.toLowerCase(), allowOverlapping, 0L); | |
} | |
/** | |
* Test if value ends with search. The search is case sensitive. | |
* | |
* @param value input string | |
* @param search string to search | |
* @return true or false | |
*/ | |
public static boolean endsWith(final String value, final String search) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return endsWith(value, search, value.length(), true); | |
} | |
/** | |
* Test if value ends with search. | |
* | |
* @param value input string | |
* @param search string to search | |
* @param caseSensitive true or false | |
* @return true or false | |
*/ | |
public static boolean endsWith(final String value, final String search, final boolean caseSensitive) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return endsWith(value, search, value.length(), caseSensitive); | |
} | |
/** | |
* Test if value ends with search. | |
* | |
* @param value input string | |
* @param search string to search | |
* @param position position till which you want to search. | |
* @param caseSensitive true or false | |
* @return true or false | |
*/ | |
public static boolean endsWith(final String value, final String search, final int position, final boolean caseSensitive) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
int remainingLength = position - search.length(); | |
if (caseSensitive) { | |
return value.indexOf(search, remainingLength) > -1; | |
} | |
return value.toLowerCase().indexOf(search.toLowerCase(), remainingLength) > -1; | |
} | |
/** | |
* Ensures that the value begins with prefix. If it doesn't exist, it's prepended. It is case sensitive. | |
* | |
* @param value input | |
* @param prefix prefix | |
* @return string with prefix if it was not present. | |
*/ | |
public static String ensureLeft(final String value, final String prefix) { | |
return ensureLeft(value, prefix, true); | |
} | |
/** | |
* Ensures that the value begins with prefix. If it doesn't exist, it's prepended. | |
* | |
* @param value input | |
* @param prefix prefix | |
* @param caseSensitive true or false | |
* @return string with prefix if it was not present. | |
*/ | |
public static String ensureLeft(final String value, final String prefix, final boolean caseSensitive) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
if (caseSensitive) { | |
return value.startsWith(prefix) ? value : prefix + value; | |
} | |
String _value = value.toLowerCase(); | |
String _prefix = prefix.toLowerCase(); | |
return _value.startsWith(_prefix) ? value : prefix + value; | |
} | |
/** | |
* Decodes data encoded with MIME base64 | |
* | |
* @param value The data to decode | |
* @return decoded data | |
*/ | |
public static String base64Decode(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return new String(Base64.getDecoder().decode(value)); | |
} | |
/** | |
* Encodes data with MIME base64. | |
* | |
* @param value The data to encode | |
* @return The encoded String | |
*/ | |
public static String base64Encode(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return Base64.getEncoder().encodeToString(value.getBytes()); | |
} | |
/** | |
* Convert binary unicode (16 digits) string to string chars | |
* | |
* @param value The value to decode | |
* @return The decoded String | |
*/ | |
public static String binDecode(final String value) { | |
return decode(value, 16, 2); | |
} | |
/** | |
* Convert string chars to binary unicode (16 digits) | |
* | |
* @param value The value to encode | |
* @return String in binary format | |
*/ | |
public static String binEncode(final String value) { | |
return encode(value, 16, 2); | |
} | |
/** | |
* Convert decimal unicode (5 digits) string to string chars | |
* | |
* @param value The value to decode | |
* @return decoded String | |
*/ | |
public static String decDecode(final String value) { | |
return decode(value, 5, 10); | |
} | |
/** | |
* Convert string chars to decimal unicode (5 digits) | |
* | |
* @param value The value to encode | |
* @return Encoded value | |
*/ | |
public static String decEncode(final String value) { | |
return encode(value, 5, 10); | |
} | |
/** | |
* Ensures that the value ends with suffix. If it doesn't, it's appended. This operation is case sensitive. | |
* | |
* @param value The input String | |
* @param suffix The substr to be ensured to be right | |
* @return The string which is guarenteed to start with substr | |
*/ | |
public static String ensureRight(final String value, final String suffix) { | |
return ensureRight(value, suffix, true); | |
} | |
/** | |
* Ensures that the value ends with suffix. If it doesn't, it's appended. | |
* | |
* @param value The input String | |
* @param suffix The substr to be ensured to be right | |
* @param caseSensitive Use case (in-)sensitive matching for determining if value already ends with suffix | |
* @return The string which is guarenteed to start with substr | |
*/ | |
public static String ensureRight(final String value, final String suffix, boolean caseSensitive) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return endsWith(value, suffix, caseSensitive) ? value : append(value, suffix); | |
} | |
/** | |
* Returns the first n chars of String | |
* | |
* @param value The input String | |
* @param n Number of chars to return | |
* @return The first n chars | |
*/ | |
public static String first(final String value, final int n) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return value.substring(0, n); | |
} | |
/** | |
* Return the first char of String | |
* | |
* @param value The input String | |
* @return The first char | |
*/ | |
public static String head(final String value) { | |
return first(value, 1); | |
} | |
/** | |
* Formats a string using parameters | |
* | |
* @param value The value to be formatted | |
* @param params Parameters to be described in the string | |
* @return The formatted string | |
*/ | |
public static String format(final String value, String... params) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
Pattern p = Pattern.compile("\\{(\\w+)\\}"); | |
Matcher m = p.matcher(value); | |
String result = value; | |
while (m.find()) { | |
int paramNumber = Integer.parseInt(m.group(1)); | |
if (params == null || paramNumber >= params.length) { | |
throw new IllegalArgumentException("params does not have value for " + m.group()); | |
} | |
result = result.replace(m.group(), params[paramNumber]); | |
} | |
return result; | |
} | |
/** | |
* Convert hexadecimal unicode (4 digits) string to string chars | |
* | |
* @param value The value to decode | |
* @return The decoded String | |
*/ | |
public static String hexDecode(final String value) { | |
return decode(value, 4, 16); | |
} | |
/** | |
* Convert string chars to hexadecimal unicode (4 digits) | |
* | |
* @param value The value to encode | |
* @return String in hexadecimal format. | |
*/ | |
public static String hexEncode(final String value) { | |
return encode(value, 4, 16); | |
} | |
/** | |
* The indexOf() method returns the index within the calling String of the first occurrence of the specified value, starting the search at fromIndex. | |
* Returns -1 if the value is not found. | |
* | |
* @param value The input String | |
* @param needle The search String | |
* @param offset The offset to start searching from. | |
* @param caseSensitive boolean to indicate whether search should be case sensitive | |
* @return Returns position of first occurrence of needle. | |
*/ | |
public static int indexOf(final String value, final String needle, int offset, boolean caseSensitive) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
if (caseSensitive) { | |
return value.indexOf(needle, offset); | |
} | |
return value.toLowerCase().indexOf(needle.toLowerCase(), offset); | |
} | |
/** | |
* Tests if two Strings are inequal | |
* | |
* @param first The first String | |
* @param second The second String | |
* @return true if first and second are not equal false otherwise | |
*/ | |
public static boolean unequal(final String first, final String second) { | |
return !Objects.equals(first, second); | |
} | |
/** | |
* Tests if two Strings are inequal | |
* | |
* @param first The first String | |
* @param second The second String | |
* @return true if first and second are not equal false otherwise | |
* @deprecated use unequal instead | |
*/ | |
public static boolean inequal(final String first, final String second) { | |
return !Objects.equals(first, second); | |
} | |
/** | |
* Inserts 'substr' into the 'value' at the 'index' provided. | |
* | |
* @param value The input String | |
* @param substr The String to insert | |
* @param index The index to insert substr | |
* @return String with substr added | |
*/ | |
public static String insert(final String value, final String substr, final int index) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
validate(substr, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
if (index > value.length()) { | |
return value; | |
} | |
return append(value.substring(0, index), substr, value.substring(index)); | |
} | |
/** | |
* Verifies if String is uppercase | |
* | |
* @param value The input String | |
* @return true if String is uppercase false otherwise | |
*/ | |
public static boolean isUpperCase(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
for (int i = 0; i < value.length(); i++) { | |
if (Character.isLowerCase(value.charAt(i))) { | |
return false; | |
} | |
} | |
return true; | |
} | |
/** | |
* Verifies if String is lower case | |
* | |
* @param value The input String | |
* @return true if String is lowercase false otherwise | |
*/ | |
public static boolean isLowerCase(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
for (int i = 0; i < value.length(); i++) { | |
if (Character.isUpperCase(value.charAt(i))) { | |
return false; | |
} | |
} | |
return true; | |
} | |
/** | |
* Return the last n chars of String | |
* | |
* @param value The input String | |
* @param n Number of chars to return | |
* @return n Last characters | |
*/ | |
public static String last(final String value, int n) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
if (n > value.length()) { | |
return value; | |
} | |
return value.substring(value.length() - n); | |
} | |
/** | |
* Returns a new string of a given length such that the beginning of the string is padded. | |
* | |
* @param value The input String | |
* @param pad The pad | |
* @param length Length of the String we want | |
* @return Padded String | |
*/ | |
public static String leftPad(final String value, final String pad, final int length) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
validate(pad, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
if (value.length() > length) { | |
return value; | |
} | |
return append(repeat(pad, length - value.length()), value); | |
} | |
/** | |
* Checks whether Object is String | |
* | |
* @param value The input String | |
* @return true if Object is a String false otherwise | |
*/ | |
public static boolean isString(final Object value) { | |
if (Objects.isNull(value)) { | |
throw new IllegalArgumentException("value can't be null"); | |
} | |
return value instanceof String; | |
} | |
/** | |
* This method returns the index within the calling String object of the last occurrence of the specified value, searching backwards from the offset. | |
* Returns -1 if the value is not found. The search starts from the end and case sensitive. | |
* | |
* @param value The input String | |
* @param needle The search String | |
* @return Return position of the last occurrence of 'needle'. | |
*/ | |
public static int lastIndexOf(final String value, final String needle) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return lastIndexOf(value, needle, value.length(), true); | |
} | |
/** | |
* This method returns the index within the calling String object of the last occurrence of the specified value, searching backwards from the offset. | |
* Returns -1 if the value is not found. The search starts from the end and case sensitive. | |
* | |
* @param value The input String | |
* @param needle The search String | |
* @param caseSensitive true or false | |
* @return Return position of the last occurrence of 'needle'. | |
*/ | |
public static int lastIndexOf(final String value, final String needle, boolean caseSensitive) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return lastIndexOf(value, needle, value.length(), caseSensitive); | |
} | |
/** | |
* This method returns the index within the calling String object of the last occurrence of the specified value, searching backwards from the offset. | |
* Returns -1 if the value is not found. | |
* | |
* @param value The input String | |
* @param needle The search String | |
* @param offset The index to start search from | |
* @param caseSensitive whether search should be case sensitive | |
* @return Return position of the last occurrence of 'needle'. | |
*/ | |
public static int lastIndexOf(final String value, final String needle, final int offset, final boolean caseSensitive) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
validate(needle, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
if (caseSensitive) { | |
return value.lastIndexOf(needle, offset); | |
} | |
return value.toLowerCase().lastIndexOf(needle.toLowerCase(), offset); | |
} | |
/** | |
* Removes all spaces on left | |
* | |
* @param value The input String | |
* @return String without left border spaces | |
*/ | |
public static String leftTrim(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return value.replaceAll("^\\s+", ""); | |
} | |
/** | |
* Returns length of String. Delegates to java.lang.String length method. | |
* | |
* @param value The input String | |
* @return Length of the String | |
*/ | |
public static int length(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return value.length(); | |
} | |
/** | |
* Return a new String starting with prepends | |
* | |
* @param value The input String | |
* @param prepends Strings to prepend | |
* @return The prepended String | |
*/ | |
public static String prepend(final String value, final String... prepends) { | |
return prependArray(value, prepends); | |
} | |
/** | |
* Return a new String starting with prepends | |
* | |
* @param value The input String | |
* @param prepends Strings to prepend | |
* @return The prepended String | |
*/ | |
public static String prependArray(final String value, final String[] prepends) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
if (prepends == null || prepends.length == 0) { | |
return value; | |
} | |
StringJoiner joiner = new StringJoiner(""); | |
for (String prepend : prepends) { | |
joiner.add(prepend); | |
} | |
return joiner.toString() + value; | |
} | |
/** | |
* Remove empty Strings from string array | |
* | |
* @param strings Array of String to be cleaned | |
* @return Array of String without empty Strings | |
*/ | |
public static String[] removeEmptyStrings(String[] strings) { | |
if (Objects.isNull(strings)) { | |
throw new IllegalArgumentException("Input array should not be null"); | |
} | |
return Arrays.stream(strings).filter(str -> str != null && !str.trim().isEmpty()).toArray(String[]::new); | |
} | |
/** | |
* Returns a new String with the prefix removed, if present. This is case sensitive. | |
* | |
* @param value The input String | |
* @param prefix String to remove on left | |
* @return The String without prefix | |
*/ | |
public static String removeLeft(final String value, final String prefix) { | |
return removeLeft(value, prefix, true); | |
} | |
/** | |
* Returns a new String with the prefix removed, if present. | |
* | |
* @param value The input String | |
* @param prefix String to remove on left | |
* @param caseSensitive ensure case sensitivity | |
* @return The String without prefix | |
*/ | |
public static String removeLeft(final String value, final String prefix, final boolean caseSensitive) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
validate(prefix, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
if (caseSensitive) { | |
return value.startsWith(prefix) ? value.substring(prefix.length()) : value; | |
} | |
return value.toLowerCase().startsWith(prefix.toLowerCase()) ? value.substring(prefix.length()) : value; | |
} | |
/** | |
* Remove all non word characters. | |
* | |
* @param value The input String | |
* @return String without non-word characters | |
*/ | |
public static String removeNonWords(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return value.replaceAll("[^\\w]+", ""); | |
} | |
/** | |
* Returns a new string with the 'suffix' removed, if present. Search is case sensitive. | |
* | |
* @param value The input String | |
* @param suffix The suffix to remove | |
* @return The String without suffix! | |
*/ | |
public static String removeRight(final String value, final String suffix) { | |
return removeRight(value, suffix, true); | |
} | |
/** | |
* Returns a new string with the 'suffix' removed, if present. | |
* | |
* @param value The input String | |
* @param suffix The suffix to remove | |
* @param caseSensitive whether search should be case sensitive or not | |
* @return The String without suffix! | |
*/ | |
public static String removeRight(final String value, final String suffix, final boolean caseSensitive) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
validate(suffix, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return endsWith(value, suffix, caseSensitive) ? value.substring(0, value.toLowerCase().lastIndexOf(suffix.toLowerCase())) : value; | |
} | |
/** | |
* Remove all spaces and replace for value. | |
* | |
* @param value The input String | |
* @return String without spaces | |
*/ | |
public static String removeSpaces(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return value.replaceAll("\\s", ""); | |
} | |
/** | |
* Returns a repeated string given a multiplier. | |
* | |
* @param value The input String | |
* @param multiplier Number of repeats | |
* @return The String repeated | |
*/ | |
public static String repeat(final String value, final int multiplier) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return Stream.generate(() -> value).limit(multiplier).collect(joining()); | |
} | |
/** | |
* Replace all occurrences of 'search' value to 'newvalue'. Uses String replace method. | |
* | |
* @param value The input | |
* @param search The String to search | |
* @param newValue The String to replace | |
* @param caseSensitive whether search should be case sensitive or not | |
* @return String replaced with 'newvalue'. | |
*/ | |
public static String replace(final String value, final String search, final String newValue, final boolean caseSensitive) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
validate(search, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
if (caseSensitive) { | |
return value.replace(search, newValue); | |
} | |
return Pattern.compile(search, Pattern.CASE_INSENSITIVE).matcher(value).replaceAll(Matcher.quoteReplacement(newValue)); | |
} | |
/** | |
* Reverse the input String | |
* | |
* @param value The input String | |
* @return Reversed String | |
*/ | |
public static String reverse(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return new StringBuilder(value).reverse().toString(); | |
} | |
/** | |
* Returns a new string of a given length such that the ending of the string is padded. | |
* | |
* @param value The input String | |
* @param length Max length of String. | |
* @param pad Character to repeat | |
* @return Right padded String | |
*/ | |
public static String rightPad(final String value, String pad, final int length) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
if (value.length() > length) { | |
return value; | |
} | |
return append(value, repeat(pad, length - value.length())); | |
} | |
/** | |
* Remove all spaces on right. | |
* | |
* @param value The String | |
* @return String without right boarders spaces. | |
*/ | |
public static String rightTrim(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return value.replaceAll("\\s+$", ""); | |
} | |
/** | |
* Truncate the string securely, not cutting a word in half. It always returns the last full word. | |
* | |
* @param value The input String | |
* @param length Max size of the truncated String | |
* @param filler String that will be added to the end of the return string. Example: '...' | |
* @return The truncated String | |
*/ | |
public static String safeTruncate(final String value, final int length, final String filler) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
if (length == 0) { | |
return ""; | |
} | |
if (length >= value.length()) { | |
return value; | |
} | |
String[] words = words(value); | |
StringJoiner result = new StringJoiner(" "); | |
int spaceCount = 0; | |
for (String word : words) { | |
if (result.length() + word.length() + filler.length() + spaceCount > length) { | |
break; | |
} else { | |
result.add(word); | |
spaceCount++; | |
} | |
} | |
return append(result.toString(), filler); | |
} | |
/** | |
* Alias to String split function. Defined only for completeness. | |
* | |
* @param value The input String | |
* @param regex The delimiting regular expression | |
* @return String Array | |
*/ | |
public static String[] split(final String value, final String regex) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return value.split(regex); | |
} | |
/** | |
* Splits a String to words | |
* | |
* @param value The input String | |
* @return Words Array | |
*/ | |
public static String[] words(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return value.split("\\W+"); | |
} | |
/** | |
* Truncate the unsecured form string, cutting the independent string of required position. | |
* | |
* @param value Value will be truncated unsecurely. | |
* @param length Size of the returned string. | |
* @param filler Value that will be added to the end of the return string. Example: '...' | |
* @return String truncated unsafely. | |
*/ | |
public static String truncate(final String value, final int length, final String filler) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
if (length == 0) { | |
return ""; | |
} | |
if (length >= value.length()) { | |
return value; | |
} | |
return append(value.substring(0, length - filler.length()), filler); | |
} | |
/** | |
* Converts all HTML entities to applicable characters. | |
* | |
* @param encodedHtml The encoded HTML | |
* @return The decoded HTML | |
*/ | |
public static String htmlDecode(final String encodedHtml) { | |
validate(encodedHtml, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
String[] entities = encodedHtml.split("&\\W+;"); | |
return Arrays.stream(entities).map(e -> HtmlEntities.decodedEntities.get(e)).collect(joining()); | |
} | |
/** | |
* Convert all applicable characters to HTML entities. | |
* | |
* @param html The HTML to encode | |
* @return The encoded data | |
*/ | |
public static String htmlEncode(final String html) { | |
validate(html, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return html.chars().mapToObj(c -> "\\u" + String.format("%04x", c).toUpperCase()).map(e -> HtmlEntities.encodedEntities.get(e)).collect(joining()); | |
} | |
/** | |
* It returns a string with its characters in random order. | |
* | |
* @param value The input String | |
* @return The shuffled String | |
*/ | |
public static String shuffle(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
String[] chars = chars(value); | |
Random random = new Random(); | |
for (int i = 0; i < chars.length; i++) { | |
int r = random.nextInt(chars.length); | |
String tmp = chars[i]; | |
chars[i] = chars[r]; | |
chars[r] = tmp; | |
} | |
return Arrays.stream(chars).collect(joining()); | |
} | |
/** | |
* Alias of substring method | |
* | |
* @param value The input String | |
* @param begin Start of slice. | |
* @param end End of slice. | |
* @return The String sliced! | |
*/ | |
public static String slice(final String value, int begin, int end) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return value.substring(begin, end); | |
} | |
/** | |
* Convert a String to a slug | |
* | |
* @param value The value to slugify | |
* @return The slugified value | |
*/ | |
public static String slugify(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
String transliterated = transliterate(collapseWhitespace(value.trim().toLowerCase())); | |
return Arrays.stream(words(transliterated.replace("&", "-and-"))).collect(joining("-")); | |
} | |
/** | |
* Remove all non valid characters. | |
* | |
* @param value The input String | |
* @return String without non valid characters. | |
*/ | |
public static String transliterate(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
String result = value; | |
Set<Map.Entry<String, List<String>>> entries = Ascii.ascii.entrySet(); | |
for (Map.Entry<String, List<String>> entry : entries) { | |
for (String ch : entry.getValue()) { | |
result = result.replace(ch, entry.getKey()); | |
} | |
} | |
return result; | |
} | |
/** | |
* Surrounds a 'value' with the given 'prefix' and 'suffix'. | |
* | |
* @param value The input String | |
* @param prefix prefix. If suffix is null then prefix is used | |
* @param suffix suffix | |
* @return The String with surround substrs! | |
*/ | |
public static String surround(final String value, final String prefix, final String suffix) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
String _prefix = Optional.ofNullable(prefix).orElse(""); | |
return append(_prefix, value, Optional.ofNullable(suffix).orElse(_prefix)); | |
} | |
/** | |
* Transform to camelCase | |
* | |
* @param value The input String | |
* @return String in camelCase. | |
*/ | |
public static String toCamelCase(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
String str = toStudlyCase(value); | |
return str.substring(0, 1).toLowerCase() + str.substring(1); | |
} | |
/** | |
* Transform to StudlyCaps. | |
* | |
* @param value The input String | |
* @return String in StudlyCaps. | |
*/ | |
public static String toStudlyCase(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
String[] words = collapseWhitespace(value.trim()).split("\\s*(_|-|\\s)\\s*"); | |
return Arrays.stream(words).filter(w -> !w.trim().isEmpty()).map(w -> head(w).toUpperCase() + tail(w)).collect(joining()); | |
} | |
/** | |
* Return tail of the String | |
* | |
* @param value The input String | |
* @return String tail | |
*/ | |
public static String tail(final String value) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return last(value, value.length() - 1); | |
} | |
/** | |
* Decamelize String | |
* | |
* @param value The input String | |
* @param chr string to use | |
* @return String decamelized. | |
*/ | |
public static String toDecamelize(final String value, final String chr) { | |
String camelCasedString = toCamelCase(value); | |
String[] words = camelCasedString.split("(?=\\p{Upper})"); | |
return Arrays.stream(words).map(String::toLowerCase).collect(joining(Optional.ofNullable(chr).orElse(" "))); | |
} | |
/** | |
* Transform to kebab-case. | |
* | |
* @param value The input String | |
* @return String in kebab-case. | |
*/ | |
public static String toKebabCase(final String value) { | |
return toDecamelize(value, "-"); | |
} | |
/** | |
* Transform to snake_case. | |
* | |
* @param value The input String | |
* @return String in snake_case. | |
*/ | |
public static String toSnakeCase(final String value) { | |
return toDecamelize(value, "_"); | |
} | |
public static String decode(final String value, final int digits, final int radix) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return Arrays | |
.stream(value.split("(?<=\\G.{" + digits + "})")) | |
.map(data -> String.valueOf(Character.toChars(Integer.parseInt(data, radix)))) | |
.collect(joining()); | |
} | |
public static String encode(final String value, final int digits, final int radix) { | |
validate(value, NULL_STRING_PREDICATE, NULL_STRING_MSG_SUPPLIER); | |
return value.chars().mapToObj(ch -> leftPad(Integer.toString(ch, radix), "0", digits)).collect(joining()); | |
} | |
private static void validate(String value, Predicate<String> predicate, final Supplier<String> supplier) { | |
if (predicate.test(value)) { | |
throw new IllegalArgumentException(supplier.get()); | |
} | |
} | |
private static long countSubstr(String value, String subStr, boolean allowOverlapping, long count) { | |
int position = value.indexOf(subStr); | |
if (position == -1) { | |
return count; | |
} | |
int offset; | |
if (!allowOverlapping) { | |
offset = position + subStr.length(); | |
} else { | |
offset = position + 1; | |
} | |
return countSubstr(value.substring(offset), subStr, allowOverlapping, ++count); | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import strman.Strman; | |
import java.util.Arrays; | |
import java.util.Optional; | |
public class StrmanTest { | |
public static void main(String[] args) { | |
// append 在一个字符串后追加任意个数的字符串 | |
String s1 = Strman.append("f", "o", "o", "b", "a", "r"); | |
System.out.println("append:" + s1); // result => "foobar" | |
// prepend 在一个字符串前追加任意个数的字符串 | |
String s1pre = Strman.prepend("r", "f", "o", "o", "b", "a"); | |
System.out.println("prepend:" + s1pre); // result => "foobar" | |
// appendArray 在一个字符串后先后追加一个字符串数组中的元素 | |
String s2 = Strman.appendArray("f", new String[]{"o", "o", "b", "a", "r"}); | |
System.out.println("append:" + s2); // result => "foobar" | |
// at 根据字符串的索引获取到对应的字符。如果索引是负数,则逆向获取,超出则抛出异常 | |
Optional<String> s3 = Strman.at("foobar", 3); | |
System.out.println("at:" + s3.get()); // result => "b" | |
// between 得到一个字符串中,开始字符串和结束字符串之间的字符串的数组 | |
String[] s4 = Strman.between("[abc], [def]", "[", "]"); | |
System.out.println("between:" + Arrays.toString(s4)); // result => "[abc, def]" | |
// chars 得到一个字符串中所有字符构成的字符串数组 | |
String[] s5 = Strman.chars("title"); | |
System.out.println("chars:" + Arrays.toString(s5)); // result => "[t, i, t, l, e]" | |
// collapseWhitespace 替换掉连续的多个空格为一个空格 | |
String s6 = Strman.collapseWhitespace("foo bar"); | |
System.out.println("chars:" + s6); // result => "foo bar" | |
// contains 判断一个字符串是否包含另外一个字符串,第三个参数,表示字符串大小写是否敏感 | |
boolean s7 = Strman.contains("foo bar", "foo"); | |
boolean s8 = Strman.contains("foo bar", "FOO", false); | |
System.out.println("contains:" + s7 + ", " + s8); // result => "true, true" | |
// containsAll 判断一个字符串是否包含某字符串数组中的所有元素 | |
boolean s9 = Strman.containsAll("foo bar", new String[]{"foo", "bar"}); | |
boolean s10 = Strman.containsAll("foo bar", new String[]{"FOO", "bar"}, false); | |
System.out.println("containsAll:" + s9 + ", " + s10); // result => "true, true" | |
// containsAny 判断一个字符串是否包含某字符串数组中的任意一个元素 | |
boolean s11 = Strman.containsAny("foo bar", new String[]{"FOO", "BAR", "Test"}, false); | |
System.out.println("containsAny:" + s11); // result => "true" | |
// countSubstr 判断一个字符串包含某字符串的个数 | |
long s12 = Strman.countSubstr("aaaAAAaaa", "aaa"); | |
long s13 = Strman.countSubstr("aaaAAAaaa", "aaa", false, false); | |
System.out.println("countSubstr:" + s12 + ", " + s13); // result => "2, 3" | |
// endsWith 判断一个字符串是否以某个字符串结尾 | |
boolean s14 = Strman.endsWith("foo bar", "bar"); | |
boolean s15 = Strman.endsWith("foo bar", "BAR", false); | |
System.out.println("endsWith:" + s14 + ", " + s15); // result => "true, true" | |
// ensureLeft 确保一个字符串以某个字符串开头,如果不是,则在前面追加该字符串,并将字符串结果返回 | |
String s16 = Strman.ensureLeft("foobar", "foo"); | |
String s17 = Strman.ensureLeft("bar", "foo"); | |
String s18 = Strman.ensureLeft("foobar", "FOO", false); | |
System.out.println("ensureLeft:" + s16 + ", " + s17 + ", " + s18); | |
// result => "foobar, foobar, foobar" | |
// ensureRight 确保一个字符串以某个字符串开头,如果不是,则在前面追加该字符串,并将字符串结果返回 | |
String s16r = Strman.ensureRight("foobar", "bar"); | |
String s17r = Strman.ensureRight("foo", "bar"); | |
String s18r = Strman.ensureRight("fooBAR", "bar", false); | |
System.out.println("ensureRight:" + s16r + ", " + s17r + ", " + s18r); | |
// result => "foobar, foobar, fooBAR" | |
// base64Encode 将字符串转成Base64编码的字符串 | |
String s19 = Strman.base64Encode("strman"); | |
System.out.println("base64Encode:" + s19); // result => "c3RybWFu" | |
// binDecode 将二进制编码(16位)转成字符串字符 | |
String s20 = Strman.binDecode("0000000001000001"); | |
System.out.println("binDecode:" + s20); // result => "A" | |
// binEncode 将字符串字符转成二进制编码(16位) | |
String s21 = Strman.binEncode("A"); | |
System.out.println("binEncode:" + s21); // result => "0000000001000001" | |
// decDecode 将十进制编码(5位)转成字符串字符 | |
String s22 = Strman.decDecode("00065"); | |
System.out.println("decDecode:" + s22); // result => "A" | |
// decEncode 将字符串转成十进制编码(5位) | |
String s23 = Strman.decEncode("A"); | |
System.out.println("decEncode:" + s23); // result => "00065" | |
// first 得到从字符串开始到索引n的字符串 | |
String s24 = Strman.first("foobar", 3); | |
System.out.println("first:" + s24); // result => "foo" | |
// last 得到从字符串结尾倒数索引n的字符串 | |
String s24l = Strman.last("foobar", 3); | |
System.out.println("last:" + s24l); // result => "bar" | |
// head 得到字符串的第一个字符 | |
String s25 = Strman.head("foobar"); | |
System.out.println("head:" + s25); // result => "f" | |
// hexDecode 将字符串字符转成十六进制编码(4位) | |
String s26 = Strman.hexDecode("0041"); | |
System.out.println("hexDecode:" + s26); // result => "A" | |
// hexEncode 将十六进制编码(4位)转成字符串字符 | |
String s27 = Strman.hexEncode("A"); | |
System.out.println("hexEncode:" + s27); // result => "0041" | |
// inequal 测试两个字符串是否相等 | |
boolean s28 = Strman.inequal("a", "b"); | |
System.out.println("inequal:" + s28); // result => "true" | |
// insert 将子字符串插入到字符串某索引位置处 | |
String s29 = Strman.insert("fbar", "oo", 1); | |
System.out.println("insert:" + s29); // result => "foobar" | |
// leftPad 将字符串从左补齐直到总长度为n为止 | |
String s30 = Strman.leftPad("1", "0", 5); | |
System.out.println("leftPad:" + s30); // result => "00001" | |
// rightPad 将字符串从右补齐直到总长度为n为止 | |
String s30r = Strman.rightPad("1", "0", 5); | |
System.out.println("rightPad:" + s30r); // result => "10000" | |
// lastIndexOf 此方法返回在指定值的最后一个发生的调用字符串对象中的索引,从偏移量中向后搜索 | |
int s31 = Strman.lastIndexOf("foobarfoobar", "F", false); | |
System.out.println("lastIndexOf:" + s31); // result => "6" | |
// leftTrim 移除字符串最左边的所有空格 | |
String s32 = Strman.leftTrim(" strman "); | |
System.out.println("leftTrim:" + s32); // result => "strman " | |
// rightTrim 移除字符串最右边的所有空格 | |
String s32r = Strman.rightTrim(" strman "); | |
System.out.println("rightTrim:" + s32r); // result => " strman" | |
// removeEmptyStrings 移除字符串数组中的空字符串 | |
String[] s33 = Strman.removeEmptyStrings(new String[]{"aa", "", " ", "bb", "cc", null}); | |
System.out.println("removeEmptyStrings:" + Arrays.toString(s33)); | |
// result => "[aa, bb, cc]" | |
// removeLeft 得到去掉前缀(如果存在的话)后的新字符串 | |
String s34 = Strman.removeLeft("foobar", "foo"); | |
System.out.println("removeLeft:" + s34); // result => "bar" | |
// removeRight 得到去掉后缀(如果存在的话)后的新字符串 | |
String s34r = Strman.removeRight("foobar", "bar"); | |
System.out.println("removeRight:" + s34r); // result => "foo" | |
// removeNonWords 得到去掉不是字符的字符串 | |
String s35 = Strman.removeNonWords("foo&bar-"); | |
System.out.println("removeNonWords:" + s35); // result => "foobar" | |
// removeSpaces 移除所有空格 | |
String s36 = Strman.removeSpaces(" str man "); | |
System.out.println("removeSpaces:" + s36); // result => " strman" | |
// repeat 得到给定字符串和重复次数的新字符串 | |
String s37 = Strman.repeat("1", 3); | |
System.out.println("repeat:" + s37); // result => "111" | |
// reverse 得到反转后的字符串 | |
String s38 = Strman.reverse("foobar"); | |
System.out.println("reverse:" + s38); // result => "raboof" | |
// safeTruncate 安全的截断字符串,不切一个字的一半,它总是返回最后一个完整的单词 | |
String s39 = Strman.safeTruncate("A Javascript string manipulation library.", 19, "..."); | |
System.out.println("safeTruncate:" + s39); // result => "A Javascript..." | |
// truncate 不太安全的截断字符串 | |
String s40 = Strman.truncate("A Javascript string manipulation library.", 19, "..."); | |
System.out.println("truncate:" + s40); // result => "A Javascript str..." | |
// htmlDecode 将html字符反转义 | |
String s41 = Strman.htmlDecode("Ш"); | |
System.out.println("htmlDecode:" + s41); // result => "Ш" | |
// htmlEncode 将html字符转义 | |
String s42 = Strman.htmlEncode("Ш"); | |
System.out.println("htmlEncode:" + s42); // result => "Ш" | |
// shuffle 将给定字符串转成随机字符顺序的字符串 | |
String s43 = Strman.shuffle("shekhar"); | |
System.out.println("shuffle:" + s43); // result => "rhsheak" | |
// slugify 将字符串分段(用"-"分段) | |
String s44 = Strman.slugify("foo bar"); | |
System.out.println("slugify:" + s44); // result => "foo-bar" | |
// transliterate 删除所有非有效字符,如:á => a | |
String s45 = Strman.transliterate("fóõ bár"); | |
System.out.println("transliterate:" + s45); // result => "foo bar" | |
// surround 给定的“前缀”和“后缀”来包裹一个字符串 | |
String s46 = Strman.surround("div", "<", ">"); | |
System.out.println("surround:" + s46); // result => "<div>" | |
// tail 得到去掉第一个字符后的字符串 | |
String s47 = Strman.tail("foobar"); | |
System.out.println("tail:" + s47); // result => "oobar" | |
// toCamelCase 转成驼峰式的字符串 | |
String s48 = Strman.toCamelCase("Camel Case"); | |
String s48_2 = Strman.toCamelCase("camel-case"); | |
System.out.println("tail:" + s48 + ", " + s48_2); // result => "camelCase, camelCase" | |
// toStudlyCase 转成Studly式的字符串 | |
String s49 = Strman.toStudlyCase("hello world"); | |
System.out.println("toStudlyCase:" + s49); // result => "HelloWorld" | |
// toDecamelize 转成Decamelize式的字符串 | |
String s50 = Strman.toDecamelize("helloWorld", null); | |
System.out.println("toDecamelize:" + s50); // result => "hello world" | |
// toKebabCase 转成Kebab式的字符串 | |
String s51 = Strman.toKebabCase("hello World"); | |
System.out.println("toKebabCase:" + s51); // result => "hello-world" | |
// toSnakeCase 转成Snake式的字符串 | |
String s52 = Strman.toSnakeCase("hello world"); | |
System.out.println("toSnakeCase:" + s52); // result => "hello_world" | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment