/* lang/tags/LANG_3_2_1/src/main/java/org/apache/commons/lang3/StringUtils.java * * Licensed to the Apache Software Foundation (ASF) under one or more * contributor license agreements. See the NOTICE file distributed with * this work for additional information regarding copyright ownership. * The ASF licenses this file to You 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 org.apache.commons.lang3; import java.util.Iterator; /** * <p>Operations on {@link java.lang.String} that are * {@code null} safe.</p> * * <ul> * <li><b>IsEmpty/IsBlank</b> * - checks if a String contains text</li> * <li><b>Trim/Strip</b> * - removes leading and trailing whitespace</li> * <li><b>Equals</b> * - compares two strings null-safe</li> * <li><b>startsWith</b> * - check if a String starts with a prefix null-safe</li> * <li><b>endsWith</b> * - check if a String ends with a suffix null-safe</li> * <li><b>IndexOf/LastIndexOf/Contains</b> * - null-safe index-of checks * <li><b>IndexOfAny/LastIndexOfAny/IndexOfAnyBut/LastIndexOfAnyBut</b> * - index-of any of a set of Strings</li> * <li><b>ContainsOnly/ContainsNone/ContainsAny</b> * - does String contains only/none/any of these characters</li> * <li><b>Substring/Left/Right/Mid</b> * - null-safe substring extractions</li> * <li><b>SubstringBefore/SubstringAfter/SubstringBetween</b> * - substring extraction relative to other strings</li> * <li><b>Split/Join</b> * - splits a String into an array of substrings and vice versa</li> * <li><b>Remove/Delete</b> * - removes part of a String</li> * <li><b>Replace/Overlay</b> * - Searches a String and replaces one String with another</li> * <li><b>Chomp/Chop</b> * - removes the last part of a String</li> * <li><b>AppendIfMissing</b> * - appends a suffix to the end of the String if not present</li> * <li><b>PrependIfMissing</b> * - prepends a prefix to the start of the String if not present</li> * <li><b>LeftPad/RightPad/Center/Repeat</b> * - pads a String</li> * <li><b>UpperCase/LowerCase/SwapCase/Capitalize/Uncapitalize</b> * - changes the case of a String</li> * <li><b>CountMatches</b> * - counts the number of occurrences of one String in another</li> * <li><b>IsAlpha/IsNumeric/IsWhitespace/IsAsciiPrintable</b> * - checks the characters in a String</li> * <li><b>DefaultString</b> * - protects against a null input String</li> * <li><b>Reverse/ReverseDelimited</b> * - reverses a String</li> * <li><b>Abbreviate</b> * - abbreviates a string using ellipsis</li> * <li><b>Difference</b> * - compares Strings and reports on their differences</li> * <li><b>LevenshteinDistance</b> * - the number of changes needed to change one String into another</li> * </ul> * * <p>The {@code StringUtils} class defines certain words related to * String handling.</p> * * <ul> * <li>null - {@code null}</li> * <li>empty - a zero-length string ({@code ""})</li> * <li>space - the space character ({@code ' '}, char 32)</li> * <li>whitespace - the characters defined by {@link Character#isWhitespace(char)}</li> * <li>trim - the characters <= 32 as in {@link String#trim()}</li> * </ul> * * <p>{@code StringUtils} handles {@code null} input Strings quietly. * That is to say that a {@code null} input will return {@code null}. * Where a {@code boolean} or {@code int} is being returned * details vary by method.</p> * * <p>A side effect of the {@code null} handling is that a * {@code NullPointerException} should be considered a bug in * {@code StringUtils}.</p> * * <p>Methods in this class give sample code to explain their operation. * The symbol {@code *} is used to indicate any input including {@code null}.</p> * * <p>#ThreadSafe#</p> * @see java.lang.String * @since 1.0 * @version $Id$ */ //@Immutable public class StringUtils { /** * The empty String {@code ""}. * @since 2.0 */ public static final String EMPTY = ""; // Joining //----------------------------------------------------------------------- /** * <p>Joins the elements of the provided array into a single String * containing the provided list of elements.</p> * * <p>No separator is added to the joined String. * Null objects or empty strings within the array are represented by * empty strings.</p> * * <pre> * StringUtils.join(null) = null * StringUtils.join([]) = "" * StringUtils.join([null]) = "" * StringUtils.join(["a", "b", "c"]) = "abc" * StringUtils.join([null, "", "a"]) = "a" * </pre> * * @param <T> the specific type of values to join together * @param elements the values to join together, may be null * @return the joined String, {@code null} if null array input * @since 2.0 * @since 3.0 Changed signature to use varargs */ public static <T> String join(final T... elements) { return join(elements, null); } /** * <p>Joins the elements of the provided array into a single String * containing the provided list of elements.</p> * * <p>No delimiter is added before or after the list. * Null objects or empty strings within the array are represented by * empty strings.</p> * * <pre> * StringUtils.join(null, *) = null * StringUtils.join([], *) = "" * StringUtils.join([null], *) = "" * StringUtils.join(["a", "b", "c"], ';') = "a;b;c" * StringUtils.join(["a", "b", "c"], null) = "abc" * StringUtils.join([null, "", "a"], ';') = ";;a" * </pre> * * @param array the array of values to join together, may be null * @param separator the separator character to use * @return the joined String, {@code null} if null array input * @since 2.0 */ public static String join(final Object[] array, final char separator) { if (array == null) { return null; } return join(array, separator, 0, array.length); } /** * <p>Joins the elements of the provided array into a single String * containing the provided list of elements.</p> * * <p>No delimiter is added before or after the list. * Null objects or empty strings within the array are represented by * empty strings.</p> * * <pre> * StringUtils.join(null, *) = null * StringUtils.join([], *) = "" * StringUtils.join([null], *) = "" * StringUtils.join(["a", "b", "c"], ';') = "a;b;c" * StringUtils.join(["a", "b", "c"], null) = "abc" * StringUtils.join([null, "", "a"], ';') = ";;a" * </pre> * * @param array the array of values to join together, may be null * @param separator the separator character to use * @param startIndex the first index to start joining from. It is * an error to pass in an end index past the end of the array * @param endIndex the index to stop joining from (exclusive). It is * an error to pass in an end index past the end of the array * @return the joined String, {@code null} if null array input * @since 2.0 */ public static String join(final Object[] array, final char separator, final int startIndex, final int endIndex) { if (array == null) { return null; } final int noOfItems = endIndex - startIndex; if (noOfItems <= 0) { return EMPTY; } final StringBuilder buf = new StringBuilder(noOfItems * 16); for (int i = startIndex; i < endIndex; i++) { if (i > startIndex) { buf.append(separator); } if (array[i] != null) { buf.append(array[i]); } } return buf.toString(); } /** * <p>Joins the elements of the provided array into a single String * containing the provided list of elements.</p> * * <p>No delimiter is added before or after the list. * A {@code null} separator is the same as an empty String (""). * Null objects or empty strings within the array are represented by * empty strings.</p> * * <pre> * StringUtils.join(null, *) = null * StringUtils.join([], *) = "" * StringUtils.join([null], *) = "" * StringUtils.join(["a", "b", "c"], "--") = "a--b--c" * StringUtils.join(["a", "b", "c"], null) = "abc" * StringUtils.join(["a", "b", "c"], "") = "abc" * StringUtils.join([null, "", "a"], ',') = ",,a" * </pre> * * @param array the array of values to join together, may be null * @param separator the separator character to use, null treated as "" * @return the joined String, {@code null} if null array input */ public static String join(final Object[] array, final String separator) { if (array == null) { return null; } return join(array, separator, 0, array.length); } /** * <p>Joins the elements of the provided array into a single String * containing the provided list of elements.</p> * * <p>No delimiter is added before or after the list. * A {@code null} separator is the same as an empty String (""). * Null objects or empty strings within the array are represented by * empty strings.</p> * * <pre> * StringUtils.join(null, *, *, *) = null * StringUtils.join([], *, *, *) = "" * StringUtils.join([null], *, *, *) = "" * StringUtils.join(["a", "b", "c"], "--", 0, 3) = "a--b--c" * StringUtils.join(["a", "b", "c"], "--", 1, 3) = "b--c" * StringUtils.join(["a", "b", "c"], "--", 2, 3) = "c" * StringUtils.join(["a", "b", "c"], "--", 2, 2) = "" * StringUtils.join(["a", "b", "c"], null, 0, 3) = "abc" * StringUtils.join(["a", "b", "c"], "", 0, 3) = "abc" * StringUtils.join([null, "", "a"], ',', 0, 3) = ",,a" * </pre> * * @param array the array of values to join together, may be null * @param separator the separator character to use, null treated as "" * @param startIndex the first index to start joining from. * @param endIndex the index to stop joining from (exclusive). * @return the joined String, {@code null} if null array input; or the empty string * if {@code endIndex - startIndex <= 0}. The number of joined entries is given by * {@code endIndex - startIndex} * @throws ArrayIndexOutOfBoundsException ife<br/> * {@code startIndex < 0} or <br/> * {@code startIndex >= array.length()} or <br/> * {@code endIndex < 0} or <br/> * {@code endIndex > array.length()} */ public static String join(final Object[] array, String separator, final int startIndex, final int endIndex) { if (array == null) { return null; } if (separator == null) { separator = EMPTY; } // endIndex - startIndex > 0: Len = NofStrings *(len(firstString) + len(separator)) // (Assuming that all Strings are roughly equally long) final int noOfItems = endIndex - startIndex; if (noOfItems <= 0) { return EMPTY; } final StringBuilder buf = new StringBuilder(noOfItems * 16); for (int i = startIndex; i < endIndex; i++) { if (i > startIndex) { buf.append(separator); } if (array[i] != null) { buf.append(array[i]); } } return buf.toString(); } /** * <p>Joins the elements of the provided {@code Iterator} into * a single String containing the provided elements.</p> * * <p>No delimiter is added before or after the list. Null objects or empty * strings within the iteration are represented by empty strings.</p> * * <p>See the examples here: {@link #join(Object[],char)}. </p> * * @param iterator the {@code Iterator} of values to join together, may be null * @param separator the separator character to use * @return the joined String, {@code null} if null iterator input * @since 2.0 */ public static String join(final Iterator<?> iterator, final char separator) { // handle null, zero and one elements before building a buffer if (iterator == null) { return null; } if (!iterator.hasNext()) { return EMPTY; } final Object first = iterator.next(); if (!iterator.hasNext()) { return ObjectUtils.toString(first); } // two or more elements final StringBuilder buf = new StringBuilder(256); // Java default is 16, probably too small if (first != null) { buf.append(first); } while (iterator.hasNext()) { buf.append(separator); final Object obj = iterator.next(); if (obj != null) { buf.append(obj); } } return buf.toString(); } /** * <p>Joins the elements of the provided {@code Iterator} into * a single String containing the provided elements.</p> * * <p>No delimiter is added before or after the list. * A {@code null} separator is the same as an empty String ("").</p> * * <p>See the examples here: {@link #join(Object[],String)}. </p> * * @param iterator the {@code Iterator} of values to join together, may be null * @param separator the separator character to use, null treated as "" * @return the joined String, {@code null} if null iterator input */ public static String join(final Iterator<?> iterator, final String separator) { // handle null, zero and one elements before building a buffer if (iterator == null) { return null; } if (!iterator.hasNext()) { return EMPTY; } final Object first = iterator.next(); if (!iterator.hasNext()) { return ObjectUtils.toString(first); } // two or more elements final StringBuilder buf = new StringBuilder(256); // Java default is 16, probably too small if (first != null) { buf.append(first); } while (iterator.hasNext()) { if (separator != null) { buf.append(separator); } final Object obj = iterator.next(); if (obj != null) { buf.append(obj); } } return buf.toString(); } /** * <p>Joins the elements of the provided {@code Iterable} into * a single String containing the provided elements.</p> * * <p>No delimiter is added before or after the list. Null objects or empty * strings within the iteration are represented by empty strings.</p> * * <p>See the examples here: {@link #join(Object[],char)}. </p> * * @param iterable the {@code Iterable} providing the values to join together, may be null * @param separator the separator character to use * @return the joined String, {@code null} if null iterator input * @since 2.3 */ public static String join(final Iterable<?> iterable, final char separator) { if (iterable == null) { return null; } return join(iterable.iterator(), separator); } /** * <p>Joins the elements of the provided {@code Iterable} into * a single String containing the provided elements.</p> * * <p>No delimiter is added before or after the list. * A {@code null} separator is the same as an empty String ("").</p> * * <p>See the examples here: {@link #join(Object[],String)}. </p> * * @param iterable the {@code Iterable} providing the values to join together, may be null * @param separator the separator character to use, null treated as "" * @return the joined String, {@code null} if null iterator input * @since 2.3 */ public static String join(final Iterable<?> iterable, final String separator) { if (iterable == null) { return null; } return join(iterable.iterator(), separator); } }