Revert "[ISSUE #3102] Create utils class to nacos-common (#4165)" (#4191)

This reverts commit cf92d19d03.
This commit is contained in:
杨翊 SionYang 2020-11-10 18:21:59 +08:00 committed by GitHub
parent f808ffdb65
commit 8950304f03
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 6 additions and 1177 deletions

View File

@ -1,175 +0,0 @@
/*
* Copyright 1999-2018 Alibaba Group Holding Ltd.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.alibaba.nacos.common.utils;
import java.lang.reflect.Array;
/**
* nacos array util.
*
* @author wujian
*/
public class ArrayUtil {
/**
* The index value when an element is not found in a list or array: {@code -1}. This value is returned by methods in
* this class and can also be used in comparisons with values returned by various method from {@link
* java.util.List}.
*/
public static final int INDEX_NOT_FOUND = -1;
/**
* An empty immutable {@code boolean} array.
*/
public static final boolean[] EMPTY_BOOLEAN_ARRAY = new boolean[0];
/**
* An empty immutable {@code String} array.
*/
public static final String[] EMPTY_STRING_ARRAY = new String[0];
/**
* Checks if an array of Objects is empty or {@code null}.
*
* @param array the array to test
* @return {@code true} if the array is empty or {@code null}
*/
public static boolean isEmpty(final Object[] array) {
return getLength(array) == 0;
}
/**
* Returns the length of the specified array. This method can deal with {@code Object} arrays and with primitive
* arrays.
*
* <p>If the input array is {@code null}, {@code 0} is returned.
*
* <pre>
* ArrayUtils.getLength(null) = 0
* ArrayUtils.getLength([]) = 0
* ArrayUtils.getLength([null]) = 1
* ArrayUtils.getLength([true, false]) = 2
* ArrayUtils.getLength([1, 2, 3]) = 3
* ArrayUtils.getLength(["a", "b", "c"]) = 3
* </pre>
*
* @param array the array to retrieve the length from, may be null
* @return The length of the array, or {@code 0} if the array is {@code null}
* @throws IllegalArgumentException if the object argument is not an array.
*/
public static int getLength(final Object array) {
if (array == null) {
return 0;
}
return Array.getLength(array);
}
/**
* Checks if the object is in the given array.
*
* <p>The method returns {@code false} if a {@code null} array is passed in.
*
* @param array the array to search through
* @param objectToFind the object to find
* @return {@code true} if the array contains the object
*/
public static boolean contains(final Object[] array, final Object objectToFind) {
return indexOf(array, objectToFind) != INDEX_NOT_FOUND;
}
// Boolean array converters
// ----------------------------------------------------------------------
/**
* <p>Converts an array of object Booleans to primitives.</p>
*
* <p>This method returns {@code null} for a {@code null} input array.</p>
*
* @param array a {@code Boolean} array, may be {@code null}
* @return a {@code boolean} array, {@code null} if null array input
* @throws NullPointerException if array content is {@code null}
*/
public static boolean[] toPrimitive(final Boolean[] array) {
if (array == null) {
return null;
} else if (array.length == 0) {
return EMPTY_BOOLEAN_ARRAY;
}
final boolean[] result = new boolean[array.length];
for (int i = 0; i < array.length; i++) {
result[i] = array[i].booleanValue();
}
return result;
}
// IndexOf search
// ----------------------------------------------------------------------
// Object IndexOf
//-----------------------------------------------------------------------
/**
* Finds the index of the given object in the array.
*
* <p>This method returns {@link #INDEX_NOT_FOUND} ({@code -1}) for a {@code null} input array.
*
* @param array the array to search through for the object, may be {@code null}
* @param objectToFind the object to find, may be {@code null}
* @return the index of the object within the array, {@link #INDEX_NOT_FOUND} ({@code -1}) if not found or {@code
* null} array input
*/
public static int indexOf(final Object[] array, final Object objectToFind) {
return indexOf(array, objectToFind, 0);
}
/**
* Finds the index of the given object in the array starting at the given index.
*
* <p>This method returns {@link #INDEX_NOT_FOUND} ({@code -1}) for a {@code null} input array.
*
* <p>A negative startIndex is treated as zero. A startIndex larger than the array
* length will return {@link #INDEX_NOT_FOUND} ({@code -1}).
*
* @param array the array to search through for the object, may be {@code null}
* @param objectToFind the object to find, may be {@code null}
* @param startIndex the index to start searching at
* @return the index of the object within the array starting at the index, {@link #INDEX_NOT_FOUND} ({@code -1}) if
* not found or {@code null} array input
*/
public static int indexOf(final Object[] array, final Object objectToFind, int startIndex) {
if (array == null) {
return INDEX_NOT_FOUND;
}
if (startIndex < 0) {
startIndex = 0;
}
if (objectToFind == null) {
for (int i = startIndex; i < array.length; i++) {
if (array[i] == null) {
return i;
}
}
} else {
for (int i = startIndex; i < array.length; i++) {
if (objectToFind.equals(array[i])) {
return i;
}
}
}
return INDEX_NOT_FOUND;
}
}

View File

@ -1,90 +0,0 @@
/*
* Copyright 1999-2018 Alibaba Group Holding Ltd.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.alibaba.nacos.common.utils;
/**
* nacos boolean util.
*
* @author wujian
*/
public class BooleanUtil {
/**
* <p>Performs an and on a set of booleans.</p>
*
* <pre>
* BooleanUtils.and(true, true) = true
* BooleanUtils.and(false, false) = false
* BooleanUtils.and(true, false) = false
* BooleanUtils.and(true, true, false) = false
* BooleanUtils.and(true, true, true) = true
* </pre>
*
* @param array an array of {@code boolean}s
* @return {@code true} if the and is successful.
* @throws IllegalArgumentException if {@code array} is {@code null}
* @throws IllegalArgumentException if {@code array} is empty.
*/
public static boolean and(final boolean... array) {
// Validates input
if (array == null) {
throw new IllegalArgumentException("The Array must not be null");
}
if (array.length == 0) {
throw new IllegalArgumentException("Array is empty");
}
for (final boolean element : array) {
if (!element) {
return false;
}
}
return true;
}
/**
* <p>Performs an and on an array of Booleans.</p>
*
* <pre>
* BooleanUtils.and(Boolean.TRUE, Boolean.TRUE) = Boolean.TRUE
* BooleanUtils.and(Boolean.FALSE, Boolean.FALSE) = Boolean.FALSE
* BooleanUtils.and(Boolean.TRUE, Boolean.FALSE) = Boolean.FALSE
* BooleanUtils.and(Boolean.TRUE, Boolean.TRUE, Boolean.TRUE) = Boolean.TRUE
* BooleanUtils.and(Boolean.FALSE, Boolean.FALSE, Boolean.TRUE) = Boolean.FALSE
* BooleanUtils.and(Boolean.TRUE, Boolean.FALSE, Boolean.TRUE) = Boolean.FALSE
* </pre>
*
* @param array an array of {@code Boolean}s
* @return {@code true} if the and is successful.
* @throws IllegalArgumentException if {@code array} is {@code null}
* @throws IllegalArgumentException if {@code array} is empty.
* @throws IllegalArgumentException if {@code array} contains a {@code null}
*/
public static Boolean and(final Boolean... array) {
if (array == null) {
throw new IllegalArgumentException("The Array must not be null");
}
if (array.length == 0) {
throw new IllegalArgumentException("Array is empty");
}
try {
final boolean[] primitive = ArrayUtil.toPrimitive(array);
return and(primitive) ? Boolean.TRUE : Boolean.FALSE;
} catch (final NullPointerException ex) {
throw new IllegalArgumentException("The array must not contain any null elements");
}
}
}

View File

@ -245,79 +245,6 @@ public final class ConvertUtils {
} }
} }
/** // end
* <p>Convert a <code>String</code> to a <code>double</code>, returning a
* default value if the conversion fails.</p>
*
* <p>If the string <code>str</code> is <code>null</code>, the default
* value is returned.</p>
*
* <pre>
* NumberUtils.toDouble(null, 1.1d) = 1.1d
* NumberUtils.toDouble("", 1.1d) = 1.1d
* NumberUtils.toDouble("1.5", 0.0d) = 1.5d
* </pre>
*
* @param str the string to convert, may be <code>null</code>
* @param defaultValue the default value
* @return the double represented by the string, or defaultValue if conversion fails
*/
public static double toDouble(final String str, final double defaultValue) {
if (str == null) {
return defaultValue;
}
try {
return Double.parseDouble(str);
} catch (final NumberFormatException nfe) {
return defaultValue;
}
}
/**
* <p>Convert a <code>String</code> to a <code>float</code>, returning
* <code>0.0f</code> if the conversion fails.</p>
*
* <p>If the string <code>str</code> is <code>null</code>,
* <code>0.0f</code> is returned.</p>
*
* <pre>
* NumberUtils.toFloat(null) = 0.0f
* NumberUtils.toFloat("") = 0.0f
* NumberUtils.toFloat("1.5") = 1.5f
* </pre>
*
* @param str the string to convert, may be <code>null</code>
* @return the float represented by the string, or <code>0.0f</code> if conversion fails
*/
public static float toFloat(final String str) {
return toFloat(str, 0.0f);
}
/**
* <p>Convert a <code>String</code> to a <code>float</code>, returning a
* default value if the conversion fails.</p>
*
* <p>If the string <code>str</code> is <code>null</code>, the default
* value is returned.</p>
*
* <pre>
* NumberUtils.toFloat(null, 1.1f) = 1.0f
* NumberUtils.toFloat("", 1.1f) = 1.1f
* NumberUtils.toFloat("1.5", 0.0f) = 1.5f
* </pre>
*
* @param str the string to convert, may be <code>null</code>
* @param defaultValue the default value
* @return the float represented by the string, or defaultValue if conversion fails
*/
public static float toFloat(final String str, final float defaultValue) {
if (str == null) {
return defaultValue;
}
try {
return Float.parseFloat(str);
} catch (final NumberFormatException nfe) {
return defaultValue;
}
}
} }

View File

@ -1,177 +0,0 @@
/*
* Copyright 1999-2018 Alibaba Group Holding Ltd.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.alibaba.nacos.common.utils;
/**
* nacos Number util.
*
* @author wujian
*/
public class NumberUtil {
/**
* <p>Checks whether the String a valid Java number.</p>
*
* <p>Valid numbers include hexadecimal marked with the <code>0x</code> or
* <code>0X</code> qualifier, octal numbers, scientific notation and
* numbers marked with a type qualifier (e.g. 123L).</p>
*
* <p>Non-hexadecimal strings beginning with a leading zero are
* treated as octal values. Thus the string <code>09</code> will return
* <code>false</code>, since <code>9</code> is not a valid octal value.
* However, numbers beginning with {@code 0.} are treated as decimal.</p>
*
* <p><code>null</code> and empty/blank {@code String} will return
* <code>false</code>.</p>
*
* @param str the <code>String</code> to check
* @return <code>true</code> if the string is a correctly formatted number
*/
public static boolean isNumber(final String str) {
return isCreatable(str);
}
/**
* <p>Checks whether the String a valid Java number.</p>
*
* <p>Valid numbers include hexadecimal marked with the <code>0x</code> or
* <code>0X</code> qualifier, octal numbers, scientific notation and
* numbers marked with a type qualifier (e.g. 123L).</p>
*
* <p>Non-hexadecimal strings beginning with a leading zero are
* treated as octal values. Thus the string <code>09</code> will return
* <code>false</code>, since <code>9</code> is not a valid octal value.
* However, numbers beginning with {@code 0.} are treated as decimal.</p>
*
* <p><code>null</code> and empty/blank {@code String} will return
* <code>false</code>.</p>
*
* @param str the <code>String</code> to check
* @return <code>true</code> if the string is a correctly formatted number
*/
@SuppressWarnings({"PMD.UndefineMagicConstantRule", "PMD.AvoidComplexConditionRule"})
public static boolean isCreatable(final String str) {
if (StringUtils.isEmpty(str)) {
return false;
}
final char[] chars = str.toCharArray();
int sz = chars.length;
boolean hasExp = false;
boolean hasDecPoint = false;
boolean allowSigns = false;
boolean foundDigit = false;
// deal with any possible sign up front
final int start = chars[0] == '-' || chars[0] == '+' ? 1 : 0;
// leading 0, skip if is a decimal number
if (sz > start + 1 && chars[start] == '0' && !StringUtils.contains(str, '.')) {
// leading 0x/0X
if (chars[start + 1] == 'x' || chars[start + 1] == 'X') {
int i = start + 2;
if (i == sz) {
// str == "0x"
return false;
}
// checking hex (it can't be anything else)
for (; i < chars.length; i++) {
if ((chars[i] < '0' || chars[i] > '9') && (chars[i] < 'a' || chars[i] > 'f') && (chars[i] < 'A'
|| chars[i] > 'F')) {
return false;
}
}
return true;
} else if (Character.isDigit(chars[start + 1])) {
// leading 0, but not hex, must be octal
int i = start + 1;
for (; i < chars.length; i++) {
if (chars[i] < '0' || chars[i] > '7') {
return false;
}
}
return true;
}
}
sz--; // don't want to loop to the last char, check it afterwords
// for type qualifiers
int i = start;
// loop to the next to last char or to the last char if we need another digit to
// make a valid number (e.g. chars[0..5] = "1234E")
while (i < sz || i < sz + 1 && allowSigns && !foundDigit) {
if (chars[i] >= '0' && chars[i] <= '9') {
foundDigit = true;
allowSigns = false;
} else if (chars[i] == '.') {
if (hasDecPoint || hasExp) {
// two decimal points or dec in exponent
return false;
}
hasDecPoint = true;
} else if (chars[i] == 'e' || chars[i] == 'E') {
// we've already taken care of hex.
if (hasExp) {
// two E's
return false;
}
if (!foundDigit) {
return false;
}
hasExp = true;
allowSigns = true;
} else if (chars[i] == '+' || chars[i] == '-') {
if (!allowSigns) {
return false;
}
allowSigns = false;
// we need a digit after the E
foundDigit = false;
} else {
return false;
}
i++;
}
if (i < chars.length) {
if (chars[i] >= '0' && chars[i] <= '9') {
// no type qualifier, OK
return true;
}
if (chars[i] == 'e' || chars[i] == 'E') {
// can't have an E at the last byte
return false;
}
if (chars[i] == '.') {
if (hasDecPoint || hasExp) {
// two decimal points or dec in exponent
return false;
}
// single trailing decimal point after non-exponent is ok
return foundDigit;
}
if (!allowSigns && (chars[i] == 'd' || chars[i] == 'D' || chars[i] == 'f' || chars[i] == 'F')) {
return foundDigit;
}
if (chars[i] == 'l' || chars[i] == 'L') {
// not allowing L with an exponent or decimal point
return foundDigit && !hasExp && !hasDecPoint;
}
// last character is illegal
return false;
}
// allowSigns is true iff the val ends in 'E'
// found digit it to make sure weird stuff like '.' and '1E-' doesn't pass
return !allowSigns && foundDigit;
}
}

View File

@ -1,104 +0,0 @@
/*
* Copyright 1999-2018 Alibaba Group Holding Ltd.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.alibaba.nacos.common.utils;
import com.google.common.base.Preconditions;
import java.util.Random;
/**
* nacos random util.
*
* @author wujian
*/
public class RandomUtil {
/**
* Random object used by random method. This has to be not local to the random method so as to not return the same
* value in the same millisecond.
*/
private static final Random RANDOM = new Random();
/**
* <p>
* Returns a random long within the specified range.
* </p>
*
* @param startInclusive the smallest value that can be returned, must be non-negative
* @param endExclusive the upper bound (not included)
* @return the random long
* @throws IllegalArgumentException if {@code startInclusive > endExclusive} or if {@code startInclusive} is
* negative
*/
public static long nextLong(final long startInclusive, final long endExclusive) {
Preconditions
.checkArgument(endExclusive >= startInclusive, "Start value must be smaller or equal to end value.");
Preconditions.checkArgument(startInclusive >= 0, "Both range values must be non-negative.");
if (startInclusive == endExclusive) {
return startInclusive;
}
return (long) nextDouble(startInclusive, endExclusive);
}
/**
* <p>
* Returns a random double within the specified range.
* </p>
*
* @param startInclusive the smallest value that can be returned, must be non-negative
* @param endInclusive the upper bound (included)
* @return the random double
* @throws IllegalArgumentException if {@code startInclusive > endInclusive} or if {@code startInclusive} is
* negative
*/
public static double nextDouble(final double startInclusive, final double endInclusive) {
Preconditions
.checkArgument(endInclusive >= startInclusive, "Start value must be smaller or equal to end value.");
Preconditions.checkArgument(startInclusive >= 0, "Both range values must be non-negative.");
if (startInclusive == endInclusive) {
return startInclusive;
}
return startInclusive + ((endInclusive - startInclusive) * RANDOM.nextDouble());
}
/**
* <p>
* Returns a random integer within the specified range.
* </p>
*
* @param startInclusive the smallest value that can be returned, must be non-negative
* @param endExclusive the upper bound (not included)
* @return the random integer
* @throws IllegalArgumentException if {@code startInclusive > endExclusive} or if {@code startInclusive} is
* negative
*/
public static int nextInt(final int startInclusive, final int endExclusive) {
Preconditions
.checkArgument(endExclusive >= startInclusive, "Start value must be smaller or equal to end value.");
Preconditions.checkArgument(startInclusive >= 0, "Both range values must be non-negative.");
if (startInclusive == endExclusive) {
return startInclusive;
}
return startInclusive + RANDOM.nextInt(endExclusive - startInclusive);
}
}

View File

@ -22,9 +22,7 @@ import java.io.IOException;
import java.io.StringWriter; import java.io.StringWriter;
import java.io.Writer; import java.io.Writer;
import java.nio.charset.Charset; import java.nio.charset.Charset;
import java.util.ArrayList;
import java.util.Collection; import java.util.Collection;
import java.util.List;
import java.util.Locale; import java.util.Locale;
/** /**
@ -42,8 +40,6 @@ public class StringUtils {
public static final String EMPTY = ""; public static final String EMPTY = "";
public static final String LF = "\n";
public static String newStringForUtf8(byte[] bytes) { public static String newStringForUtf8(byte[] bytes) {
return new String(bytes, Charset.forName(Constants.ENCODE)); return new String(bytes, Charset.forName(Constants.ENCODE));
} }
@ -67,35 +63,6 @@ public class StringUtils {
return true; return true;
} }
/**
* <p>Checks if a CharSequence is empty (""), null or whitespace only.</p>
*
* <p>Whitespace is defined by {@link Character#isWhitespace(char)}.</p>
*
* <pre>
* StringUtils.isBlank(null) = true
* StringUtils.isBlank("") = true
* StringUtils.isBlank(" ") = true
* StringUtils.isBlank("bob") = false
* StringUtils.isBlank(" bob ") = false
* </pre>
*
* @param cs the CharSequence to check, may be null
* @return {@code true} if the CharSequence is null, empty or whitespace only
*/
public static boolean isBlank(final CharSequence cs) {
int strLen;
if (cs == null || (strLen = cs.length()) == 0) {
return true;
}
for (int i = 0; i < strLen; i++) {
if (!Character.isWhitespace(cs.charAt(i))) {
return false;
}
}
return true;
}
/** /**
* Judge whether all strings are blank. * Judge whether all strings are blank.
* *
@ -123,10 +90,6 @@ public class StringUtils {
return str == null || str.length() == 0; return str == null || str.length() == 0;
} }
public static boolean isEmpty(CharSequence cs) {
return cs == null || cs.length() == 0;
}
public static String defaultIfEmpty(String str, String defaultStr) { public static String defaultIfEmpty(String str, String defaultStr) {
return StringUtils.isEmpty(str) ? defaultStr : str; return StringUtils.isEmpty(str) ? defaultStr : str;
} }
@ -313,6 +276,8 @@ public class StringUtils {
* @param searchStr the CharSequence to find, may be null * @param searchStr the CharSequence to find, may be null
* @return true if the CharSequence contains the search CharSequence irrespective of case or false if not or {@code * @return true if the CharSequence contains the search CharSequence irrespective of case or false if not or {@code
* null} string input * null} string input
* @since 3.0 Changed signature from containsIgnoreCase(String, String) to containsIgnoreCase(CharSequence,
* CharSequence)
*/ */
public static boolean containsIgnoreCase(final CharSequence str, final CharSequence searchStr) { public static boolean containsIgnoreCase(final CharSequence str, final CharSequence searchStr) {
if (str == null || searchStr == null) { if (str == null || searchStr == null) {
@ -388,6 +353,8 @@ public class StringUtils {
* @param str1 the first CharSequence, may be null * @param str1 the first CharSequence, may be null
* @param str2 the second CharSequence, may be null * @param str2 the second CharSequence, may be null
* @return {@code true} if the CharSequence are equal, case insensitive, or both {@code null} * @return {@code true} if the CharSequence are equal, case insensitive, or both {@code null}
* @since 3.0 Changed signature from equalsIgnoreCase(String, String) to equalsIgnoreCase(CharSequence,
* CharSequence)
*/ */
public static boolean equalsIgnoreCase(final CharSequence str1, final CharSequence str2) { public static boolean equalsIgnoreCase(final CharSequence str1, final CharSequence str2) {
if (str1 == null || str2 == null) { if (str1 == null || str2 == null) {
@ -445,526 +412,7 @@ public class StringUtils {
return true; return true;
} }
@SuppressWarnings("PMD.UndefineMagicConstantRule")
static int indexOf(CharSequence cs, int searchChar, int start) {
if (cs instanceof String) {
return ((String) cs).indexOf(searchChar, start);
} else {
int sz = cs.length();
if (start < 0) {
start = 0;
}
if (searchChar < 65536) {
for (int i = start; i < sz; ++i) {
if (cs.charAt(i) == searchChar) {
return i;
}
}
}
if (searchChar <= 1114111) {
char[] chars = Character.toChars(searchChar);
for (int i = start; i < sz - 1; ++i) {
char high = cs.charAt(i);
char low = cs.charAt(i + 1);
if (high == chars[0] && low == chars[1]) {
return i;
}
}
}
return -1;
}
}
static int indexOf(CharSequence cs, CharSequence searchChar, int start) {
return cs.toString().indexOf(searchChar.toString(), start);
}
} }
/** // end
* <p>Checks if CharSequence contains a search character, handling {@code null}.
* This method uses {@link String#indexOf(int)} if possible.</p>
*
* <p>A {@code null} or empty ("") CharSequence will return {@code false}.</p>
*
* <pre>
* StringUtils.contains(null, *) = false
* StringUtils.contains("", *) = false
* StringUtils.contains("abc", 'a') = true
* StringUtils.contains("abc", 'z') = false
* </pre>
*
* @param seq the CharSequence to check, may be null
* @param searchChar the character to find
* @return true if the CharSequence contains the search character, false if not or {@code null} string input
*/
public static boolean contains(final CharSequence seq, final int searchChar) {
if (isEmpty(seq)) {
return false;
}
return CharSequenceUtils.indexOf(seq, searchChar, 0) >= 0;
}
/**
* <p>Checks if CharSequence contains a search CharSequence, handling {@code null}.
* This method uses {@link String#indexOf(String)} if possible.</p>
*
* <p>A {@code null} CharSequence will return {@code false}.</p>
*
* <pre>
* StringUtils.contains(null, *) = false
* StringUtils.contains(*, null) = false
* StringUtils.contains("", "") = true
* StringUtils.contains("abc", "") = true
* StringUtils.contains("abc", "a") = true
* StringUtils.contains("abc", "z") = false
* </pre>
*
* @param seq the CharSequence to check, may be null
* @param searchSeq the CharSequence to find, may be null
* @return true if the CharSequence contains the search CharSequence, false if not or {@code null} string input
*/
public static boolean contains(final CharSequence seq, final CharSequence searchSeq) {
if (seq == null || searchSeq == null) {
return false;
}
return CharSequenceUtils.indexOf(seq, searchSeq, 0) >= 0;
}
/**
* <p>Checks if none of the CharSequences are empty (""), null or whitespace only.</p>
*
* <p>Whitespace is defined by {@link Character#isWhitespace(char)}.</p>
*
* <pre>
* StringUtils.isNoneBlank((String) null) = false
* StringUtils.isNoneBlank((String[]) null) = true
* StringUtils.isNoneBlank(null, "foo") = false
* StringUtils.isNoneBlank(null, null) = false
* StringUtils.isNoneBlank("", "bar") = false
* StringUtils.isNoneBlank("bob", "") = false
* StringUtils.isNoneBlank(" bob ", null) = false
* StringUtils.isNoneBlank(" ", "bar") = false
* StringUtils.isNoneBlank(new String[] {}) = true
* StringUtils.isNoneBlank(new String[]{""}) = false
* StringUtils.isNoneBlank("foo", "bar") = true
* </pre>
*
* @param css the CharSequences to check, may be null or empty
* @return {@code true} if none of the CharSequences are empty or null or whitespace only
*/
public static boolean isNoneBlank(final CharSequence... css) {
return !isAnyBlank(css);
}
/**
* <p>Checks if any of the CharSequences are empty ("") or null or whitespace only.</p>
*
* <p>Whitespace is defined by {@link Character#isWhitespace(char)}.</p>
*
* <pre>
* StringUtils.isAnyBlank((String) null) = true
* StringUtils.isAnyBlank((String[]) null) = false
* StringUtils.isAnyBlank(null, "foo") = true
* StringUtils.isAnyBlank(null, null) = true
* StringUtils.isAnyBlank("", "bar") = true
* StringUtils.isAnyBlank("bob", "") = true
* StringUtils.isAnyBlank(" bob ", null) = true
* StringUtils.isAnyBlank(" ", "bar") = true
* StringUtils.isAnyBlank(new String[] {}) = false
* StringUtils.isAnyBlank(new String[]{""}) = true
* StringUtils.isAnyBlank("foo", "bar") = false
* </pre>
*
* @param css the CharSequences to check, may be null or empty
* @return {@code true} if any of the CharSequences are empty or null or whitespace only
*/
public static boolean isAnyBlank(final CharSequence... css) {
if (ArrayUtil.isEmpty(css)) {
return false;
}
for (final CharSequence cs : css) {
if (isBlank(cs)) {
return true;
}
}
return false;
}
/**
* <p>Check if a CharSequence starts with a specified prefix.</p>
*
* <p>{@code null}s are handled without exceptions. Two {@code null}
* references are considered to be equal. The comparison is case sensitive.</p>
*
* <pre>
* StringUtils.startsWith(null, null) = true
* StringUtils.startsWith(null, "abc") = false
* StringUtils.startsWith("abcdef", null) = false
* StringUtils.startsWith("abcdef", "abc") = true
* StringUtils.startsWith("ABCDEF", "abc") = false
* </pre>
*
* @param str the CharSequence to check, may be null
* @param prefix the prefix to find, may be null
* @return {@code true} if the CharSequence starts with the prefix, case sensitive, or both {@code null}
*/
public static boolean startsWith(final CharSequence str, final CharSequence prefix) {
return startsWith(str, prefix, false);
}
/**
* <p>Check if a CharSequence starts with a specified prefix (optionally case insensitive).</p>
*
* @param str the CharSequence to check, may be null
* @param prefix the prefix to find, may be null
* @param ignoreCase indicates whether the compare should ignore case (case insensitive) or not.
* @return {@code true} if the CharSequence starts with the prefix or both {@code null}
* @see String#startsWith(String)
*/
private static boolean startsWith(final CharSequence str, final CharSequence prefix, final boolean ignoreCase) {
if (str == null || prefix == null) {
return str == prefix;
}
if (prefix.length() > str.length()) {
return false;
}
return CharSequenceUtils.regionMatches(str, ignoreCase, 0, prefix, 0, prefix.length());
}
/**
* <p>Deletes all whitespaces from a String as defined by
* {@link Character#isWhitespace(char)}.</p>
*
* <pre>
* StringUtils.deleteWhitespace(null) = null
* StringUtils.deleteWhitespace("") = ""
* StringUtils.deleteWhitespace("abc") = "abc"
* StringUtils.deleteWhitespace(" ab c ") = "abc"
* </pre>
*
* @param str the String to delete whitespace from, may be null
* @return the String without whitespaces, {@code null} if null String input
*/
public static String deleteWhitespace(final String str) {
if (isEmpty(str)) {
return str;
}
final int sz = str.length();
final char[] chs = new char[sz];
int count = 0;
for (int i = 0; i < sz; i++) {
if (!Character.isWhitespace(str.charAt(i))) {
chs[count++] = str.charAt(i);
}
}
if (count == sz) {
return str;
}
return new String(chs, 0, count);
}
/**
* <p>Case insensitive check if a CharSequence starts with a specified prefix.</p>
*
* <p>{@code null}s are handled without exceptions. Two {@code null}
* references are considered to be equal. The comparison is case insensitive.</p>
*
* <pre>
* StringUtils.startsWithIgnoreCase(null, null) = true
* StringUtils.startsWithIgnoreCase(null, "abc") = false
* StringUtils.startsWithIgnoreCase("abcdef", null) = false
* StringUtils.startsWithIgnoreCase("abcdef", "abc") = true
* StringUtils.startsWithIgnoreCase("ABCDEF", "abc") = true
* </pre>
*
* @param str the CharSequence to check, may be null
* @param prefix the prefix to find, may be null
* @return {@code true} if the CharSequence starts with the prefix, case insensitive, or both {@code null}
* @see java.lang.String#startsWith(String)
*/
public static boolean startsWithIgnoreCase(final CharSequence str, final CharSequence prefix) {
return startsWith(str, prefix, true);
}
// Stripping
//-----------------------------------------------------------------------
/**
* <p>Strips whitespace from the start and end of a String.</p>
*
* <p>This is similar to {@link #trim(String)} but removes whitespace.
* Whitespace is defined by {@link Character#isWhitespace(char)}.</p>
*
* <p>A {@code null} input String returns {@code null}.</p>
*
* <pre>
* StringUtils.strip(null) = null
* StringUtils.strip("") = ""
* StringUtils.strip(" ") = ""
* StringUtils.strip("abc") = "abc"
* StringUtils.strip(" abc") = "abc"
* StringUtils.strip("abc ") = "abc"
* StringUtils.strip(" abc ") = "abc"
* StringUtils.strip(" ab c ") = "ab c"
* </pre>
*
* @param str the String to remove whitespace from, may be null
* @return the stripped String, {@code null} if null String input
*/
public static String strip(final String str) {
return strip(str, null);
}
/**
* <p>Strips any of a set of characters from the start and end of a String.
* This is similar to {@link String#trim()} but allows the characters to be stripped to be controlled.</p>
*
* <p>A {@code null} input String returns {@code null}.
* An empty string ("") input returns the empty string.</p>
*
* <p>If the stripChars String is {@code null}, whitespace is
* stripped as defined by {@link Character#isWhitespace(char)}. Alternatively use {@link #strip(String)}.</p>
*
* <pre>
* StringUtils.strip(null, *) = null
* StringUtils.strip("", *) = ""
* StringUtils.strip("abc", null) = "abc"
* StringUtils.strip(" abc", null) = "abc"
* StringUtils.strip("abc ", null) = "abc"
* StringUtils.strip(" abc ", null) = "abc"
* StringUtils.strip(" abcyx", "xyz") = " abc"
* </pre>
*
* @param str the String to remove characters from, may be null
* @param stripChars the characters to remove, null treated as whitespace
* @return the stripped String, {@code null} if null String input
*/
public static String strip(String str, final String stripChars) {
if (isEmpty(str)) {
return str;
}
str = stripStart(str, stripChars);
return stripEnd(str, stripChars);
}
/**
* <p>Strips any of a set of characters from the start of a String.</p>
*
* <p>A {@code null} input String returns {@code null}.
* An empty string ("") input returns the empty string.</p>
*
* <p>If the stripChars String is {@code null}, whitespace is
* stripped as defined by {@link Character#isWhitespace(char)}.</p>
*
* <pre>
* StringUtils.stripStart(null, *) = null
* StringUtils.stripStart("", *) = ""
* StringUtils.stripStart("abc", "") = "abc"
* StringUtils.stripStart("abc", null) = "abc"
* StringUtils.stripStart(" abc", null) = "abc"
* StringUtils.stripStart("abc ", null) = "abc "
* StringUtils.stripStart(" abc ", null) = "abc "
* StringUtils.stripStart("yxabc ", "xyz") = "abc "
* </pre>
*
* @param str the String to remove characters from, may be null
* @param stripChars the characters to remove, null treated as whitespace
* @return the stripped String, {@code null} if null String input
*/
public static String stripStart(final String str, final String stripChars) {
int strLen;
if (str == null || (strLen = str.length()) == 0) {
return str;
}
int start = 0;
if (stripChars == null) {
while (start != strLen && Character.isWhitespace(str.charAt(start))) {
start++;
}
} else if (stripChars.isEmpty()) {
return str;
} else {
while (start != strLen && stripChars.indexOf(str.charAt(start)) != INDEX_NOT_FOUND) {
start++;
}
}
return str.substring(start);
}
/**
* <p>Strips any of a set of characters from the end of a String.</p>
*
* <p>A {@code null} input String returns {@code null}.
* An empty string ("") input returns the empty string.</p>
*
* <p>If the stripChars String is {@code null}, whitespace is
* stripped as defined by {@link Character#isWhitespace(char)}.</p>
*
* <pre>
* StringUtils.stripEnd(null, *) = null
* StringUtils.stripEnd("", *) = ""
* StringUtils.stripEnd("abc", "") = "abc"
* StringUtils.stripEnd("abc", null) = "abc"
* StringUtils.stripEnd(" abc", null) = " abc"
* StringUtils.stripEnd("abc ", null) = "abc"
* StringUtils.stripEnd(" abc ", null) = " abc"
* StringUtils.stripEnd(" abcyx", "xyz") = " abc"
* StringUtils.stripEnd("120.00", ".0") = "12"
* </pre>
*
* @param str the String to remove characters from, may be null
* @param stripChars the set of characters to remove, null treated as whitespace
* @return the stripped String, {@code null} if null String input
*/
public static String stripEnd(final String str, final String stripChars) {
int end;
if (str == null || (end = str.length()) == 0) {
return str;
}
if (stripChars == null) {
while (end != 0 && Character.isWhitespace(str.charAt(end - 1))) {
end--;
}
} else if (stripChars.isEmpty()) {
return str;
} else {
while (end != 0 && stripChars.indexOf(str.charAt(end - 1)) != INDEX_NOT_FOUND) {
end--;
}
}
return str.substring(0, end);
}
/**
* <p>Splits the provided text into an array, separators specified.
* This is an alternative to using StringTokenizer.</p>
*
* <p>The separator is not included in the returned String array.
* Adjacent separators are treated as one separator. For more control over the split use the StrTokenizer
* class.</p>
*
* <p>A {@code null} input String returns {@code null}.
* A {@code null} separatorChars splits on whitespace.</p>
*
* <pre>
* StringUtils.split(null, *) = null
* StringUtils.split("", *) = []
* StringUtils.split("abc def", null) = ["abc", "def"]
* StringUtils.split("abc def", " ") = ["abc", "def"]
* StringUtils.split("abc def", " ") = ["abc", "def"]
* StringUtils.split("ab:cd:ef", ":") = ["ab", "cd", "ef"]
* </pre>
*
* @param str the String to parse, may be null
* @param separatorChars the characters used as the delimiters, {@code null} splits on whitespace
* @return an array of parsed Strings, {@code null} if null String input
*/
public static String[] split(final String str, final String separatorChars) {
return splitWorker(str, separatorChars, -1, false);
}
/**
* Performs the logic for the {@code split} and {@code splitPreserveAllTokens} methods that return a maximum array
* length.
*
* @param str the String to parse, may be {@code null}
* @param separatorChars the separate character
* @param max the maximum number of elements to include in the array. A zero or negative value implies
* no limit.
* @param preserveAllTokens if {@code true}, adjacent separators are treated as empty token separators; if {@code
* false}, adjacent separators are treated as one separator.
* @return an array of parsed Strings, {@code null} if null String input
*/
@SuppressWarnings("PMD.AvoidComplexConditionRule")
private static String[] splitWorker(final String str, final String separatorChars, final int max,
final boolean preserveAllTokens) {
// Performance tuned for 2.0 (JDK1.4)
// Direct code is quicker than StringTokenizer.
// Also, StringTokenizer uses isSpace() not isWhitespace()
if (str == null) {
return null;
}
final int len = str.length();
if (len == 0) {
return ArrayUtil.EMPTY_STRING_ARRAY;
}
final List<String> list = new ArrayList<String>();
int sizePlus1 = 1;
int i = 0;
int start = 0;
boolean match = false;
boolean lastMatch = false;
if (separatorChars == null) {
// Null separator means use whitespace
while (i < len) {
if (Character.isWhitespace(str.charAt(i))) {
if (match || preserveAllTokens) {
lastMatch = true;
if (sizePlus1++ == max) {
i = len;
lastMatch = false;
}
list.add(str.substring(start, i));
match = false;
}
start = ++i;
continue;
}
lastMatch = false;
match = true;
i++;
}
} else if (separatorChars.length() == 1) {
// Optimise 1 character case
final char sep = separatorChars.charAt(0);
while (i < len) {
if (str.charAt(i) == sep) {
if (match || preserveAllTokens) {
lastMatch = true;
if (sizePlus1++ == max) {
i = len;
lastMatch = false;
}
list.add(str.substring(start, i));
match = false;
}
start = ++i;
continue;
}
lastMatch = false;
match = true;
i++;
}
} else {
// standard case
while (i < len) {
if (separatorChars.indexOf(str.charAt(i)) >= 0) {
if (match || preserveAllTokens) {
lastMatch = true;
if (sizePlus1++ == max) {
i = len;
lastMatch = false;
}
list.add(str.substring(start, i));
match = false;
}
start = ++i;
continue;
}
lastMatch = false;
match = true;
i++;
}
}
if (match || preserveAllTokens && lastMatch) {
list.add(str.substring(start, i));
}
return list.toArray(new String[list.size()]);
}
} }