0001: /*
0002: * SSHTools - Java SSH2 API
0003: *
0004: * Copyright (C) 2002-2003 Lee David Painter and Contributors.
0005: *
0006: * Contributions made by:
0007: *
0008: * Brett Smith
0009: * Richard Pernavas
0010: * Erwin Bolwidt
0011: *
0012: * This program is free software; you can redistribute it and/or
0013: * modify it under the terms of the GNU General Public License
0014: * as published by the Free Software Foundation; either version 2
0015: * of the License, or (at your option) any later version.
0016: *
0017: * This program is distributed in the hope that it will be useful,
0018: * but WITHOUT ANY WARRANTY; without even the implied warranty of
0019: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
0020: * GNU General Public License for more details.
0021: *
0022: * You should have received a copy of the GNU General Public License
0023: * along with this program; if not, write to the Free Software
0024: * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
0025: */
0026: // ===========================================================================
0027: // CONTENT : CLASS StringUtil
0028: // AUTHOR : Manfred Duchrow
0029: // VERSION : 2.0 - 21/03/2003
0030: // HISTORY :
0031: // 10/07/1999 duma CREATED
0032: // 09/12/1999 duma added -> SPACE, repeat()
0033: // moved -> from package com.mdcs.util
0034: // 25/01/2000 duma moved -> from package com.mdcs.text
0035: // 09/02/2000 duma changed -> renamed SPACE to CH_SPACE
0036: // added -> CH_CR, CH_TAB, ..., STR_SPACE, STR_NEWLINE, ...
0037: // 11/01/2002 duma added -> indexOf(), indexOfIgnoreCase(), contains(), containsIgnoreCase()
0038: // 17/05/2002 duma added -> copyFrom()
0039: // 03/07/2002 duma added -> cutHead(), prefix(), suffix()
0040: // 06/07/2002 duma added -> indexOf() and contains() for StringPattern and reverse()
0041: // 15/08/2002 duma added -> upTo(), startingFrom(), asMap()
0042: // 29/09/2002 duma added -> allParts() and allSubstrings() that don't skip empty elements
0043: // 06/03/2003 duma changed -> append() now uses System.arraycopy()
0044: // added -> remove( String[], String[] ), remove( String[], String )
0045: // removeNull( String[] )
0046: // 21/03/2003 duma added -> leftPad(), leftPadCh(), rightPad(), rightPadCh() for int values
0047: //
0048: // Copyright (c) 1999-2003, by Manfred Duchrow. All rights reserved.
0049: // ===========================================================================
0050: package com.sshtools.daemon.util;
0051:
0052: import java.io.*;
0053:
0054: import java.text.*;
0055:
0056: import java.util.*;
0057:
0058: /**
0059: * The sole instance of this class provides several convienience methods for
0060: * string manipulation such as substring replacement or character repetition.
0061: *
0062: * @author Manfred Duchrow
0063: * @version 2.0
0064: */
0065: public class StringUtil {
0066: // =========================================================================
0067: // CONSTANTS
0068: // =========================================================================
0069:
0070: /** Constant for the space character */
0071: public static final char CH_SPACE = '\u0020';
0072:
0073: /** Constant for the new line character */
0074: public static final char CH_NEWLINE = '\n';
0075:
0076: /** Constant for the carriage return character */
0077: public static final char CH_CR = '\r';
0078:
0079: /** Constant for the tabulator character */
0080: public static final char CH_TAB = '\t';
0081:
0082: /** Constant for the String representation of the space character */
0083: public static final String STR_SPACE = "\u0020";
0084:
0085: /** Constant for the String representation of the new line character */
0086: public static final String STR_NEWLINE = "\n";
0087:
0088: /**
0089: * Constant for the String representation of the carriage return character
0090: */
0091: public static final String STR_CR = "\r";
0092:
0093: /** Constant for the String representation of the tabulator character */
0094: public static final String STR_TAB = "\t";
0095: private static final String WORD_DELIM = STR_SPACE + STR_TAB
0096: + STR_NEWLINE + STR_CR;
0097:
0098: // =========================================================================
0099: // CLASS VARIABLES
0100: // =========================================================================
0101: private static StringUtil singleton = null;
0102:
0103: private static StringUtil getSingleton() {
0104: return singleton;
0105: }
0106:
0107: private static void setSingleton(StringUtil inst) {
0108: singleton = inst;
0109: }
0110:
0111: // =========================================================================
0112: // PUBLIC CLASS METHODS
0113: // =========================================================================
0114:
0115: /**
0116: * Returns the one and only instance of this class.
0117: *
0118: * @return
0119: */
0120: public static StringUtil current() {
0121: if (getSingleton() == null) {
0122: setSingleton(new StringUtil());
0123: }
0124:
0125: return getSingleton();
0126: }
0127:
0128: // current()
0129: // =========================================================================
0130: // PUBLIC INSTANCE METHODS
0131: // =========================================================================
0132:
0133: /**
0134: * Returns the given string with all found oldSubStr replaced by newSubStr. <br>
0135: * Example: StringUtil.current().replaceAll( "Seven of ten", "even", "ix"
0136: * ) ;<br>
0137: * results in: "Six of ten"
0138: *
0139: * @param sourceStr The string that should be checked for occurrences of
0140: * oldSubStr
0141: * @param oldSubStr The string that is searched for in sourceStr
0142: * @param newSubStr The new string that is placed everywhere the oldSubStr
0143: * was found
0144: *
0145: * @return The original string with all found substrings replaced by new
0146: * strings
0147: */
0148: public String replaceAll(String sourceStr, String oldSubStr,
0149: String newSubStr) {
0150: String part = null;
0151: String result = "";
0152: int index = -1;
0153: int subLen = 0;
0154: subLen = oldSubStr.length();
0155: part = sourceStr;
0156:
0157: while ((part.length() > 0) && (subLen > 0)) {
0158: index = part.indexOf(oldSubStr);
0159:
0160: if (index >= 0) {
0161: result = result + part.substring(0, index) + newSubStr;
0162: part = part.substring(index + subLen);
0163: } else {
0164: result = result + part;
0165: part = "";
0166: }
0167: }
0168:
0169: // while
0170: return result;
0171: }
0172:
0173: // replaceAll()
0174: // -------------------------------------------------------------------------
0175:
0176: /**
0177: * Returns a string with size of count and all characters initialized with
0178: * ch. <br>
0179: *
0180: * @param ch the character to be repeated in the result string.
0181: * @param count the number of times the given character should occur in the
0182: * result string.
0183: *
0184: * @return A string containing <i>count</i> characters <i>ch</i>.
0185: */
0186: public String repeat(char ch, int count) {
0187: StringBuffer buffer = null;
0188: buffer = new StringBuffer(count);
0189:
0190: for (int i = 1; i <= count; i++) {
0191: buffer.append(ch);
0192: }
0193:
0194: return (buffer.toString());
0195: }
0196:
0197: // repeat()
0198: // -------------------------------------------------------------------------
0199:
0200: /**
0201: * Returns an array of substrings of the given text. <br>
0202: * The delimiters between the substrings are the whitespace characters
0203: * SPACE, NEWLINE, CR and TAB.
0204: *
0205: * @param text The string that should be splitted into whitespace separated
0206: * words
0207: *
0208: * @return An array of substrings of the given text
0209: *
0210: * @see #parts(String, String)
0211: */
0212: public String[] words(String text) {
0213: return this .parts(text, WORD_DELIM);
0214: }
0215:
0216: // words()
0217: // -------------------------------------------------------------------------
0218:
0219: /**
0220: * Returns an array of substrings of the given text. <br>
0221: * The separators between the substrings are the given delimiters. Each
0222: * character in the delimiter string is treated as a separator. <br>
0223: * All consecutive delimiters are treated as one delimiter, that is there
0224: * will be no empty strings in the result.
0225: *
0226: * @param text The string that should be splitted into substrings
0227: * @param delimiters All characters that should be recognized as a
0228: * separator or substrings
0229: *
0230: * @return An array of substrings of the given text
0231: *
0232: * @see #allParts(String, String)
0233: * @see #substrings(String, String)
0234: * @see #allSubstrings(String, String)
0235: */
0236: public String[] parts(String text, String delimiters) {
0237: return this .parts(text, delimiters, false);
0238: }
0239:
0240: // parts()
0241: // -------------------------------------------------------------------------
0242:
0243: /**
0244: * Returns an array of substrings of the given text. <br>
0245: * The separators between the substrings are the given delimiters. Each
0246: * character in the delimiter string is treated as a separator. <br>
0247: * For each delimiter that is followed immediately by another delimiter an
0248: * empty string will be added to the result. There are no empty strings
0249: * added to the result for a delimiter at the very beginning of at the
0250: * very end.
0251: *
0252: * <p>
0253: * Examples:
0254: * </p>
0255: *
0256: * <p>
0257: * allParts( "/A/B//", "/" ) --> { "A", "B", "" }<br>
0258: * allParts( "/A,B/C;D", ",;/" ) --> { "A", "B", "C", "D" }<br>
0259: * allParts( "A/B,C/D", "," ) --> { "A/B", "C/D" }<br>
0260: * </p>
0261: *
0262: * @param text The string that should be splitted into substrings
0263: * @param delimiters All characters that should be recognized as a
0264: * separator or substrings
0265: *
0266: * @return An array of substrings of the given text
0267: *
0268: * @see #parts(String, String)
0269: * @see #substrings(String, String)
0270: * @see #allSubstrings(String, String)
0271: */
0272: public String[] allParts(String text, String delimiters) {
0273: return this .parts(text, delimiters, true);
0274: }
0275:
0276: // allParts()
0277: // -------------------------------------------------------------------------
0278:
0279: /**
0280: * Returns the given text split up into an array of strings, at the
0281: * occurrances of the separator string. In contrary to method parts() the
0282: * separator is a one or many character sequence delimiter. That is, only
0283: * the exact sequence of the characters in separator identifies the end
0284: * of a substring. Subsequent occurences of separator will be skipped.
0285: * Therefore no empty strings ("") will be in the result array.
0286: *
0287: * @param text The text to be split up
0288: * @param separator The string that separates the substrings
0289: *
0290: * @return An array of substrings not containing any separator anymore
0291: *
0292: * @see #allSubstrings(String, String)
0293: * @see #parts(String, String)
0294: * @see #allParts(String, String)
0295: */
0296: public String[] substrings(String text, String separator) {
0297: return this .substrings(text, separator, false);
0298: }
0299:
0300: // substrings()
0301: // -------------------------------------------------------------------------
0302:
0303: /**
0304: * Returns the given text split up into an array of strings, at the
0305: * occurrances of the separator string. In contrary to method allParts()
0306: * the separator is a one or many character sequence delimiter. That is,
0307: * only the exact sequence of the characters in separator identifies the
0308: * end of a substring. Subsequent occurences of separator are not skipped.
0309: * They are added as empty strings to the result.
0310: *
0311: * @param text The text to be split up
0312: * @param separator The string that separates the substrings
0313: *
0314: * @return An array of substrings not containing any separator anymore
0315: *
0316: * @see #substrings(String, String)
0317: * @see #parts(String, String)
0318: * @see #allParts(String, String)
0319: */
0320: public String[] allSubstrings(String text, String separator) {
0321: return this .substrings(text, separator, true);
0322: }
0323:
0324: // allSubstrings()
0325: // -------------------------------------------------------------------------
0326:
0327: /**
0328: * Returns the first substring that is enclosed by the specified
0329: * delimiters. <br>
0330: * The delimiters are not included in the return string.
0331: *
0332: * <p>
0333: * Example:<br> getDelimitedSubstring( "This {placeholder} belongs to me",
0334: * "{", "}" ) --> returns "placeholder"
0335: * </p>
0336: *
0337: * @param text The input string that contains the delimited part
0338: * @param startDelimiter The start delimiter of the substring
0339: * @param endDelimiter The end delimiter of the substring
0340: *
0341: * @return The substring or an empty string, if no delimiters are found.
0342: */
0343: public String getDelimitedSubstring(String text,
0344: String startDelimiter, String endDelimiter) {
0345: int start;
0346: int stop;
0347: String subStr = "";
0348:
0349: if ((text != null) && (startDelimiter != null)
0350: && (endDelimiter != null)) {
0351: start = text.indexOf(startDelimiter);
0352:
0353: if (start >= 0) {
0354: stop = text.indexOf(endDelimiter, start + 1);
0355:
0356: if (stop > start) {
0357: subStr = text.substring(start + 1, stop);
0358: }
0359: }
0360: }
0361:
0362: return subStr;
0363: }
0364:
0365: // getDelimitedSubstring()
0366: // -------------------------------------------------------------------------
0367:
0368: /**
0369: * Returns the first substring that is enclosed by the specified delimiter. <br>
0370: * The delimiters are not included in the return string.
0371: *
0372: * <p>
0373: * Example:<br> getDelimitedSubstring( "File 'text.txt' not found.", "'",
0374: * "'" ) --> returns "text.txt"
0375: * </p>
0376: *
0377: * @param text The input string that contains the delimited part
0378: * @param delimiter The start and end delimiter of the substring
0379: *
0380: * @return The substring or an empty string, if no delimiters are found.
0381: */
0382: public String getDelimitedSubstring(String text, String delimiter) {
0383: return this .getDelimitedSubstring(text, delimiter, delimiter);
0384: }
0385:
0386: // getDelimitedSubstring()
0387: // -------------------------------------------------------------------------
0388:
0389: /**
0390: * Prints the stack trace of the specified throwable to a string and
0391: * returns it.
0392: *
0393: * @param throwable
0394: *
0395: * @return
0396: */
0397: public String stackTrace(Throwable throwable) {
0398: StringWriter sw = new StringWriter();
0399: PrintWriter pw = new PrintWriter(sw);
0400: throwable.printStackTrace(pw);
0401: pw.close();
0402:
0403: return sw.toString();
0404: }
0405:
0406: // stackTrace()
0407: // -------------------------------------------------------------------------
0408:
0409: /**
0410: * Returns the given string filled (on the left) up to the specified length
0411: * with the given character. <br>
0412: * Example: leftPadCh( "12", 6, '0' ) --> "000012"
0413: *
0414: * @param str
0415: * @param len
0416: * @param ch
0417: *
0418: * @return
0419: */
0420: public String leftPadCh(String str, int len, char ch) {
0421: return this .padCh(str, len, ch, true);
0422: }
0423:
0424: // leftPadCh()
0425: // -------------------------------------------------------------------------
0426:
0427: /**
0428: * Returns the given string filled (on the left) up to the specified length
0429: * with spaces. <br>
0430: * Example: leftPad( "XX", 4 ) --> " XX"
0431: *
0432: * @param str The string that has to be filled up to the specified length
0433: * @param len The length of the result string
0434: *
0435: * @return
0436: */
0437: public String leftPad(String str, int len) {
0438: return this .leftPadCh(str, len, CH_SPACE);
0439: }
0440:
0441: // leftPad()
0442: // -------------------------------------------------------------------------
0443:
0444: /**
0445: * Returns the given integer as string filled (on the left) up to the
0446: * specified length with the given fill character. <br>
0447: * Example: leftPad( 24, 5, '' ) --> "24"
0448: *
0449: * @param value
0450: * @param len
0451: * @param fillChar
0452: *
0453: * @return
0454: */
0455: public String leftPadCh(int value, int len, char fillChar) {
0456: return this .leftPadCh(Integer.toString(value), len, fillChar);
0457: }
0458:
0459: // leftPadCh()
0460: // -------------------------------------------------------------------------
0461:
0462: /**
0463: * Returns the given integer as string filled (on the left) up to the
0464: * specified length with zeroes. <br>
0465: * Example: leftPad( 12, 4 ) --> "0012"
0466: *
0467: * @param value
0468: * @param len
0469: *
0470: * @return
0471: */
0472: public String leftPad(int value, int len) {
0473: return this .leftPadCh(value, len, '0');
0474: }
0475:
0476: // leftPad()
0477: // -------------------------------------------------------------------------
0478:
0479: /**
0480: * Returns the given string filled (on the right) up to the specified
0481: * length with the given character. <br>
0482: * Example: rightPadCh( "34", 5, 'X' ) --> "34XXX"
0483: *
0484: * @param str
0485: * @param len
0486: * @param ch
0487: *
0488: * @return
0489: */
0490: public String rightPadCh(String str, int len, char ch) {
0491: return this .padCh(str, len, ch, false);
0492: }
0493:
0494: // rightPadCh()
0495: // -------------------------------------------------------------------------
0496:
0497: /**
0498: * Returns the given string filled (on the right) up to the specified
0499: * length with spaces. <br>
0500: * Example: rightPad( "88", 6 ) --> "88 "
0501: *
0502: * @param str
0503: * @param len
0504: *
0505: * @return
0506: */
0507: public String rightPad(String str, int len) {
0508: return this .rightPadCh(str, len, CH_SPACE);
0509: }
0510:
0511: // rightPad()
0512: // -------------------------------------------------------------------------
0513:
0514: /**
0515: * Returns the given integer as string filled (on the right) up to the
0516: * specified length with the given character. <br>
0517: * Example: rightPad( "32", 4, '#' ) --> "32##"
0518: *
0519: * @param value
0520: * @param len
0521: * @param fillChar
0522: *
0523: * @return
0524: */
0525: public String rightPadCh(int value, int len, char fillChar) {
0526: return this .rightPadCh(Integer.toString(value), len, fillChar);
0527: }
0528:
0529: // rightPad()
0530: // -------------------------------------------------------------------------
0531:
0532: /**
0533: * Returns the given integer as string filled (on the right) up to the
0534: * specified length with spaces. <br>
0535: * Example: rightPad( "17", 5 ) --> "17 "
0536: *
0537: * @param value
0538: * @param len
0539: *
0540: * @return
0541: */
0542: public String rightPad(int value, int len) {
0543: return this .rightPadCh(value, len, CH_SPACE);
0544: }
0545:
0546: // rightPad()
0547: // -------------------------------------------------------------------------
0548:
0549: /**
0550: * Returns the given string filled equally left and right up to the
0551: * specified length with the given character. <br>
0552: * Example: centerCh( "A", 5, '_' ) --> "__A__" <br>
0553: * Example: centerCh( "XX", 7, '+' ) --> "++XX+++"
0554: *
0555: * @param str
0556: * @param len
0557: * @param ch
0558: *
0559: * @return
0560: */
0561: public String centerCh(String str, int len, char ch) {
0562: String buffer = null;
0563: int missing = len - str.length();
0564: int half = 0;
0565:
0566: if (missing <= 0) {
0567: return str;
0568: }
0569:
0570: half = missing / 2;
0571: buffer = this .rightPadCh(str, len - half, ch);
0572:
0573: return this .leftPadCh(buffer, len, ch);
0574: }
0575:
0576: // centerCh()
0577: // -------------------------------------------------------------------------
0578:
0579: /**
0580: * Returns the given string filled (on the right and right) up to the
0581: * specified length with spaces. <br>
0582: * Example: center( "Mike", 10 ) --> " Mike "
0583: *
0584: * @param str
0585: * @param len
0586: *
0587: * @return
0588: */
0589: public String center(String str, int len) {
0590: return this .centerCh(str, len, CH_SPACE);
0591: }
0592:
0593: // center()
0594: // -------------------------------------------------------------------------
0595:
0596: /**
0597: * Returns the given string array extended by one element that hold the
0598: * specified string.
0599: *
0600: * @param strings
0601: * @param string
0602: *
0603: * @return
0604: */
0605: public String[] append(String[] strings, String string) {
0606: String[] appStr = { string };
0607:
0608: return this .append(strings, appStr);
0609: }
0610:
0611: // append()
0612: // -------------------------------------------------------------------------
0613:
0614: /**
0615: * Returns an array of strings that contains all strings given by the first
0616: * and second string array. The strings from the second array will be
0617: * added at the end of the first array.
0618: *
0619: * @param strings The array of string to which to append
0620: * @param appendStrings The string to be appended to the first array
0621: *
0622: * @return
0623: */
0624: public String[] append(String[] strings, String[] appendStrings) {
0625: String[] newStrings = null;
0626:
0627: if (strings == null) {
0628: return appendStrings;
0629: }
0630:
0631: if (appendStrings == null) {
0632: return strings;
0633: }
0634:
0635: newStrings = new String[strings.length + appendStrings.length];
0636: System.arraycopy(strings, 0, newStrings, 0, strings.length);
0637: System.arraycopy(appendStrings, 0, newStrings, strings.length,
0638: appendStrings.length);
0639:
0640: return newStrings;
0641: }
0642:
0643: // append()
0644: // -------------------------------------------------------------------------
0645:
0646: /**
0647: * Returns an array of strings that contains all strings given in the first
0648: * plus the specified string to append, if it is not already in the given
0649: * array.
0650: *
0651: * @param strings
0652: * @param appendString
0653: *
0654: * @return
0655: */
0656: public String[] appendIfNotThere(String[] strings,
0657: String appendString) {
0658: if (this .contains(strings, appendString)) {
0659: return strings;
0660: } else {
0661: return this .append(strings, appendString);
0662: }
0663: }
0664:
0665: // appendIfNotThere()
0666: // -------------------------------------------------------------------------
0667:
0668: /**
0669: * Returns an array of strings that contains all strings given in the first
0670: * plus all strings of the second array that are not already in the first
0671: * array.
0672: *
0673: * @param strings
0674: * @param appendStrings
0675: *
0676: * @return
0677: */
0678: public String[] appendIfNotThere(String[] strings,
0679: String[] appendStrings) {
0680: String[] newStrings = strings;
0681:
0682: if (appendStrings == null) {
0683: return newStrings;
0684: }
0685:
0686: for (int i = 0; i < appendStrings.length; i++) {
0687: newStrings = this .appendIfNotThere(newStrings,
0688: appendStrings[i]);
0689: }
0690:
0691: return newStrings;
0692: }
0693:
0694: // appendIfNotThere()
0695: // -------------------------------------------------------------------------
0696:
0697: /**
0698: * Removes all string of the second array from the first array. Returns a
0699: * new array of string that contains all remaining strings of the original
0700: * strings array.
0701: *
0702: * @param strings The array from which to remove the strings
0703: * @param removeStrings The strings to be removed
0704: *
0705: * @return
0706: */
0707: public String[] remove(String[] strings, String[] removeStrings) {
0708: if ((strings == null) || (removeStrings == null)
0709: || (strings.length == 0) || (removeStrings.length == 0)) {
0710: return strings;
0711: }
0712:
0713: return this .removeFromStringArray(strings, removeStrings);
0714: }
0715:
0716: // remove()
0717: // -------------------------------------------------------------------------
0718:
0719: /**
0720: * Removes the given string from the specified string array. Returns a new
0721: * array of string that contains all remaining strings of the original
0722: * strings array.
0723: *
0724: * @param strings The array from which to remove the string
0725: * @param removeString The string to be removed
0726: *
0727: * @return
0728: */
0729: public String[] remove(String[] strings, String removeString) {
0730: String[] removeStrings = { removeString };
0731:
0732: return this .remove(strings, removeStrings);
0733: }
0734:
0735: // remove()
0736: // -------------------------------------------------------------------------
0737:
0738: /**
0739: * Removes all null values from the given string array. Returns a new
0740: * string array that contains all none null values of the input array.
0741: *
0742: * @param strings The array to be cleared of null values
0743: *
0744: * @return
0745: */
0746: public String[] removeNull(String[] strings) {
0747: if (strings == null) {
0748: return strings;
0749: }
0750:
0751: return this .removeFromStringArray(strings, null);
0752: }
0753:
0754: // removeNull()
0755: // -------------------------------------------------------------------------
0756:
0757: /**
0758: * Returns a string that contains all given strings concatenated and
0759: * separated by the specified separator.
0760: *
0761: * @param strings The array of strings that should be concatenated
0762: * @param separator The separator between the strings
0763: *
0764: * @return One string containing the concatenated strings separated by
0765: * separator
0766: */
0767: public String asString(String[] strings, String separator) {
0768: StringBuffer buffer = null;
0769: buffer = new StringBuffer(strings.length * 20);
0770:
0771: if (strings.length > 0) {
0772: buffer.append(strings[0].toString());
0773:
0774: for (int i = 1; i < strings.length; i++) {
0775: buffer.append(separator);
0776:
0777: if (strings[i] != null) {
0778: buffer.append(strings[i]);
0779: }
0780: }
0781: }
0782:
0783: return buffer.toString();
0784: }
0785:
0786: // asString()
0787: // -------------------------------------------------------------------------
0788:
0789: /**
0790: * Returns a string that contains all given strings concatenated and
0791: * separated by comma.
0792: *
0793: * @param strings The array of strings that should be concatenated
0794: *
0795: * @return One string containing the concatenated strings separated by
0796: * comma (",")
0797: */
0798: public String asString(String[] strings) {
0799: return this .asString(strings, ",");
0800: }
0801:
0802: // asString()
0803: // -------------------------------------------------------------------------
0804:
0805: /**
0806: * Returns the index of the first string in the given string array that
0807: * matches the specified string pattern. If no string is found in the
0808: * array the result is -1.
0809: *
0810: * @param strArray An array of string (may contain null elements)
0811: * @param pattern The pattern the searched string must match
0812: *
0813: * @return The index of the matching string in the array or -1 if not found
0814: */
0815: public int indexOf(String[] strArray, StringPattern pattern) {
0816: if ((strArray == null) || (strArray.length == 0)) {
0817: return -1;
0818: }
0819:
0820: boolean found = false;
0821:
0822: for (int i = 0; i < strArray.length; i++) {
0823: if (strArray[i] == null) {
0824: if (pattern == null) {
0825: found = true;
0826: }
0827: } else {
0828: if (pattern != null) {
0829: found = pattern.matches(strArray[i]);
0830: }
0831: }
0832:
0833: if (found) {
0834: return i;
0835: }
0836: }
0837:
0838: return -1;
0839: }
0840:
0841: // indexOf()
0842: // -------------------------------------------------------------------------
0843:
0844: /**
0845: * Returns the index of the specified string in the given string array. It
0846: * returns the index of the first occurrence of the string. If the string
0847: * is not found in the array the result is -1. The comparison of the
0848: * strings is case-sensitive!
0849: *
0850: * @param strArray An array of string (may contain null elements)
0851: * @param searchStr The string to be looked up in the array (null allowed)
0852: *
0853: * @return The index of the string in the array or -1 if not found
0854: */
0855: public int indexOf(String[] strArray, String searchStr) {
0856: return this .indexOfString(strArray, searchStr, false);
0857: }
0858:
0859: // indexOf()
0860: // -------------------------------------------------------------------------
0861:
0862: /**
0863: * Returns the index of the specified string in the given string array. It
0864: * returns the index of the first occurrence of the string. If the string
0865: * is not found in the array the result is -1. The comparison of the
0866: * strings is case-insensitive!
0867: *
0868: * @param strArray An array of string (may contain null elements)
0869: * @param searchStr The string to be looked up in the array (null allowed)
0870: *
0871: * @return The index of the string in the array or -1 if not found
0872: */
0873: public int indexOfIgnoreCase(String[] strArray, String searchStr) {
0874: return this .indexOfString(strArray, searchStr, true);
0875: }
0876:
0877: // indexOfIgnoreCase()
0878: // -------------------------------------------------------------------------
0879:
0880: /**
0881: * Returns whether or not the specified string can be found in the given
0882: * string array.
0883: *
0884: * @param strArray An array of string (may contain null elements)
0885: * @param searchStr The string to be looked up in the array (null allowed)
0886: * @param ignoreCase Defines whether or not the comparison is
0887: * case-sensitive.
0888: *
0889: * @return true, if the specified array contains the given string
0890: */
0891: public boolean contains(String[] strArray, String searchStr,
0892: boolean ignoreCase) {
0893: if (ignoreCase) {
0894: return this .containsIgnoreCase(strArray, searchStr);
0895: } else {
0896: return this .contains(strArray, searchStr);
0897: }
0898: }
0899:
0900: // contains()
0901: // -------------------------------------------------------------------------
0902:
0903: /**
0904: * Returns whether or not a string can be found in the given string array
0905: * that matches the specified string pattern.
0906: *
0907: * @param strArray An array of string (may contain null elements)
0908: * @param pattern The string pattern to match against in the array (null
0909: * allowed)
0910: *
0911: * @return true, if the specified array contains a string matching the
0912: * pattern
0913: */
0914: public boolean contains(String[] strArray, StringPattern pattern) {
0915: return (this .indexOf(strArray, pattern) >= 0);
0916: }
0917:
0918: // contains()
0919: // -------------------------------------------------------------------------
0920:
0921: /**
0922: * Returns whether or not the specified string can be found in the given
0923: * string array. The comparison of the strings is case-sensitive!
0924: *
0925: * @param strArray An array of string (may contain null elements)
0926: * @param searchStr The string to be looked up in the array (null allowed)
0927: *
0928: * @return true, if the specified array contains the given string
0929: */
0930: public boolean contains(String[] strArray, String searchStr) {
0931: return (this .indexOf(strArray, searchStr) >= 0);
0932: }
0933:
0934: // contains()
0935: // -------------------------------------------------------------------------
0936:
0937: /**
0938: * Returns whether or not the specified string can be found in the given
0939: * string array. The comparison of the strings is case-insensitive!
0940: *
0941: * @param strArray An array of string (may contain null elements)
0942: * @param searchStr The string to be looked up in the array (null allowed)
0943: *
0944: * @return true, if the specified array contains the given string
0945: */
0946: public boolean containsIgnoreCase(String[] strArray,
0947: String searchStr) {
0948: return (this .indexOfIgnoreCase(strArray, searchStr) >= 0);
0949: }
0950:
0951: // containsIgnoreCase()
0952: // -------------------------------------------------------------------------
0953:
0954: /**
0955: * Returns all elements of string array <i>from</i> in a new array from
0956: * index start up to the end. If start index is larger than the array's
0957: * length, an empty array will be returned.
0958: *
0959: * @param from The string array the elements should be copied from
0960: * @param start Index of the first element to copy
0961: *
0962: * @return
0963: */
0964: public String[] copyFrom(String[] from, int start) {
0965: if (from == null) {
0966: return null;
0967: }
0968:
0969: return this .copyFrom(from, start, from.length - 1);
0970: }
0971:
0972: // copyFrom()
0973: // -------------------------------------------------------------------------
0974:
0975: /**
0976: * Returns all elements of string array <i>from</i> in a new array from
0977: * index start up to index end (inclusive). If end is larger than the last
0978: * valid index, it will be reduced to the last index. If end index is less
0979: * than start index, an empty array will be returned.
0980: *
0981: * @param from The string array the elements should be copied from
0982: * @param start Index of the first element to copy
0983: * @param end Index of last element to be copied
0984: *
0985: * @return
0986: */
0987: public String[] copyFrom(String[] from, int start, int end) {
0988: String[] result;
0989: int count;
0990: int stop = end;
0991:
0992: if (from == null) {
0993: return null;
0994: }
0995:
0996: if (stop > (from.length - 1)) {
0997: stop = from.length - 1;
0998: }
0999:
1000: count = stop - start + 1;
1001:
1002: if (count < 1) {
1003: return new String[0];
1004: }
1005:
1006: result = new String[count];
1007: System.arraycopy(from, start, result, 0, count);
1008:
1009: return result;
1010: }
1011:
1012: // copyFrom()
1013: // -------------------------------------------------------------------------
1014:
1015: /**
1016: * Returns the portion of the given string that comes before the last
1017: * occurance of the specified separator. <br>
1018: * If the separator could not be found in the given string, then the
1019: * string is returned unchanged.
1020: *
1021: * <p>
1022: * Examples:
1023: * </p>
1024: *
1025: * <p>
1026: * cutTail( "A/B/C", "/" ) ; // returns "A/B" <br>
1027: * cutTail( "A/B/C", "," ) ; // returns "A/B/C"
1028: * </p>
1029: *
1030: * <p></p>
1031: *
1032: * @param text The string from which to cut off the tail
1033: * @param separator The separator from where to cut off
1034: *
1035: * @return the string without the separator and without the characters
1036: * after the separator
1037: *
1038: * @see #prefix( String, String )
1039: * @see #suffix( String, String )
1040: * @see #cutHead( String, String )
1041: * @see #startingFrom( String, String )
1042: * @see #upTo( String, String )
1043: */
1044: public String cutTail(String text, String separator) {
1045: int index;
1046:
1047: if ((text == null) || (separator == null)) {
1048: return text;
1049: }
1050:
1051: index = text.lastIndexOf(separator);
1052:
1053: if (index < 0) {
1054: return text;
1055: }
1056:
1057: return text.substring(0, index);
1058: }
1059:
1060: // cutTail()
1061: // ------------------------------------------------------------------------
1062:
1063: /**
1064: * Returns the portion of the given string that stands after the last
1065: * occurance of the specified separator. <br>
1066: * If the separator could not be found in the given string, then the
1067: * string is returned unchanged.
1068: *
1069: * <p>
1070: * Examples:
1071: * </p>
1072: *
1073: * <p>
1074: * cutHead( "A/B/C", "/" ) ; // returns "C" <br>
1075: * cutHead( "A/B/C", "," ) ; // returns "A/B/C"
1076: * </p>
1077: *
1078: * <p></p>
1079: *
1080: * @param text The string from which to cut off the head
1081: * @param separator The separator up to which to cut off
1082: *
1083: * @return the string without the separator and without the characters
1084: * before the separator
1085: *
1086: * @see #prefix( String, String )
1087: * @see #cutTail( String, String )
1088: * @see #suffix( String, String )
1089: * @see #startingFrom( String, String )
1090: * @see #upTo( String, String )
1091: */
1092: public String cutHead(String text, String separator) {
1093: int index;
1094:
1095: if ((text == null) || (separator == null)) {
1096: return text;
1097: }
1098:
1099: index = text.lastIndexOf(separator);
1100:
1101: if (index < 0) {
1102: return text;
1103: }
1104:
1105: return text.substring(index + 1);
1106: }
1107:
1108: // cutHead()
1109: // ------------------------------------------------------------------------
1110:
1111: /**
1112: * Returns a string array with two elements where the first is the
1113: * attribute name and the second is the attribute value. Splits the given
1114: * string at the first occurance of separator and returns the piece before
1115: * the separator in element 0 and the piece after the separator in the
1116: * returned array. If the separator is not found, the first element
1117: * contains the full string and the second an empty string.
1118: *
1119: * @param str The string that contains the name-value pair
1120: * @param separator The separator between name and value
1121: *
1122: * @return
1123: */
1124: public String[] splitNameValue(String str, String separator) {
1125: String[] result = { "", "" };
1126: int index;
1127:
1128: if (str != null) {
1129: index = str.indexOf(separator);
1130:
1131: if (index > 0) {
1132: result[0] = str.substring(0, index);
1133: result[1] = str.substring(index + separator.length());
1134: } else {
1135: result[0] = str;
1136: }
1137: }
1138:
1139: return result;
1140: }
1141:
1142: // splitNameValue()
1143: // -------------------------------------------------------------------------
1144:
1145: /**
1146: * Returns the substring of the given string that comes before the first
1147: * occurance of the specified separator. If the string starts with a
1148: * separator, the result will be an empty string. If the string doesn't
1149: * contain the separator the method returns null.
1150: *
1151: * <p>
1152: * Examples:
1153: * </p>
1154: *
1155: * <p>
1156: * prefix( "A/B/C", "/" ) ; // returns "A" <br>
1157: * prefix( "A/B/C", "," ) ; // returns null
1158: * </p>
1159: *
1160: * <p></p>
1161: *
1162: * @param str The string of which the prefix is desired
1163: * @param separator Separates the prefix from the rest of the string
1164: *
1165: * @return
1166: *
1167: * @see #suffix( String, String )
1168: * @see #cutTail( String, String )
1169: * @see #cutHead( String, String )
1170: * @see #startingFrom( String, String )
1171: * @see #upTo( String, String )
1172: */
1173: public String prefix(String str, String separator) {
1174: return this .prefix(str, separator, true);
1175: }
1176:
1177: // prefix()
1178: // -------------------------------------------------------------------------
1179:
1180: /**
1181: * Returns the substring of the given string that comes after the first
1182: * occurance of the specified separator. If the string ends with a
1183: * separator, the result will be an empty string. If the string doesn't
1184: * contain the separator the method returns null.
1185: *
1186: * <p>
1187: * Examples:
1188: * </p>
1189: *
1190: * <p>
1191: * suffix( "A/B/C", "/" ) ; // returns "B/C" <br>
1192: * suffix( "A/B/C", "," ) ; // returns null
1193: * </p>
1194: *
1195: * <p></p>
1196: *
1197: * @param str The string of which the suffix is desired
1198: * @param separator Separates the suffix from the rest of the string
1199: *
1200: * @return
1201: *
1202: * @see #prefix( String, String )
1203: * @see #cutTail( String, String )
1204: * @see #cutHead( String, String )
1205: * @see #startingFrom( String, String )
1206: * @see #upTo( String, String )
1207: */
1208: public String suffix(String str, String separator) {
1209: return this .suffix(str, separator, true);
1210: }
1211:
1212: // suffix()
1213: // -------------------------------------------------------------------------
1214:
1215: /**
1216: * Returns the substring of the given string that comes before the first
1217: * occurance of the specified separator. If the string starts with a
1218: * separator, the result will be an empty string. If the string doesn't
1219: * contain the separator the method returns the whole string unchanged.
1220: *
1221: * <p>
1222: * Examples:
1223: * </p>
1224: *
1225: * <p>
1226: * upTo( "A/B/C", "/" ) ; // returns "A" <br>
1227: * upTo( "A/B/C", "," ) ; // returns "A/B/C" <br>
1228: * upTo( "/A/B/C", "/" ) ; // returns ""
1229: * </p>
1230: *
1231: * <p></p>
1232: *
1233: * @param str The string of which the prefix is desired
1234: * @param separator Separates the prefix from the rest of the string
1235: *
1236: * @return
1237: *
1238: * @see #prefix( String, String )
1239: * @see #cutTail( String, String )
1240: * @see #cutHead( String, String )
1241: * @see #startingFrom( String, String )
1242: * @see #suffix( String, String )
1243: */
1244: public String upTo(String str, String separator) {
1245: return this .prefix(str, separator, false);
1246: }
1247:
1248: // upTo()
1249: // -------------------------------------------------------------------------
1250:
1251: /**
1252: * Returns the substring of the given string that comes after the first
1253: * occurance of the specified separator. If the string doesn't contain the
1254: * separator the method returns the whole string unchanged.
1255: *
1256: * <p>
1257: * Examples:
1258: * </p>
1259: *
1260: * <p>
1261: * startingFrom( "A/B/C", "/" ) ; // returns "B/C" <br>
1262: * startingFrom( "A/B/C", "," ) ; // returns "A/B/C"
1263: * </p>
1264: *
1265: * <p></p>
1266: *
1267: * @param str The string of which the suffix is desired
1268: * @param separator Separates the suffix from the rest of the string
1269: *
1270: * @return
1271: *
1272: * @see #prefix( String, String )
1273: * @see #cutTail( String, String )
1274: * @see #cutHead( String, String )
1275: * @see #suffix( String, String )
1276: * @see #upTo( String, String )
1277: */
1278: public String startingFrom(String str, String separator) {
1279: return this .suffix(str, separator, false);
1280: }
1281:
1282: // startingFrom()
1283: // -------------------------------------------------------------------------
1284:
1285: /**
1286: * Returns a string that contains all characters of the given string in
1287: * reverse order.
1288: *
1289: * @param str
1290: *
1291: * @return
1292: */
1293: public String reverse(String str) {
1294: if (str == null) {
1295: return null;
1296: }
1297:
1298: char[] newStr = new char[str.length()];
1299: StringCharacterIterator iterator = new StringCharacterIterator(
1300: str);
1301: int i = 0;
1302:
1303: for (char ch = iterator.last(); ch != CharacterIterator.DONE; ch = iterator
1304: .previous()) {
1305: newStr[i] = ch;
1306: i++;
1307: }
1308:
1309: return new String(newStr);
1310: }
1311:
1312: // reverse()
1313: // -------------------------------------------------------------------------
1314:
1315: /**
1316: * Returns the given map with new entries from the specified String. If the
1317: * specified map is null a new empty java.util.Hashtable will be created. <br>
1318: * The string is split up into elements separated by the elementSeparator
1319: * parameter. If this parameter is null the default separator "," is used. <br>
1320: * After that each part is split up to a key-value pair separated by the
1321: * keyValueSeparator parameter. If this parameter is null the default "="
1322: * is used. <br>
1323: * Then the key-value pairs are added to the map and the map is returned.
1324: *
1325: * <p>
1326: * <b>Be aware that all leading and trailing whitespaces of keys and values
1327: * will be removed!</b>
1328: * </p>
1329: *
1330: * @param str The string that contains the list of key-value pairs
1331: * @param elementSeparator The separator between the elements of the list
1332: * @param keyValueSeparator The separator between the keys and values
1333: * @param map The map to which the key-value pairs are added
1334: *
1335: * @return
1336: */
1337: public Map toMap(String str, String elementSeparator,
1338: String keyValueSeparator, Map map) {
1339: Map result;
1340: String elemSep;
1341: String kvSep;
1342: String[] assignments;
1343: String[] nameValue;
1344:
1345: if (str == null) {
1346: return map;
1347: }
1348:
1349: result = ((map == null) ? new Hashtable() : map);
1350: elemSep = (elementSeparator == null) ? "," : elementSeparator;
1351: kvSep = (keyValueSeparator == null) ? "=" : keyValueSeparator;
1352: assignments = this .parts(str, elemSep);
1353:
1354: for (int i = 0; i < assignments.length; i++) {
1355: nameValue = this .splitNameValue(assignments[i], kvSep);
1356: nameValue[0] = nameValue[0].trim();
1357: nameValue[1] = nameValue[1].trim();
1358:
1359: if (nameValue[0].length() > 0) {
1360: result.put(nameValue[0], nameValue[1]);
1361: }
1362: }
1363:
1364: return result;
1365: }
1366:
1367: // asMap()
1368: // -------------------------------------------------------------------------
1369:
1370: /**
1371: * Returns a new map object that contains all key-value pairs of the
1372: * specified string. <br>
1373: * The separator between the elements is assumed to be "," and "=" between
1374: * key and value.
1375: *
1376: * <p>
1377: * Example:<br> "main=Fred,support1=John,support2=Stella,manager=Oscar"
1378: * </p>
1379: *
1380: * <p>
1381: * <b>Be aware that all leading and trailing whitespaces of keys and values
1382: * will be removed!</b>
1383: * </p>
1384: *
1385: * @param str The string with the list of key-value pairs
1386: *
1387: * @return
1388: */
1389: public Map asMap(String str) {
1390: return this .toMap(str, null, null, null);
1391: }
1392:
1393: // asMap()
1394: // -------------------------------------------------------------------------
1395:
1396: /**
1397: * Returns a new map object that contains all key-value pairs of the
1398: * specified string. <br>
1399: * The separator between the keys and values is assumed to be "=".
1400: *
1401: * <p>
1402: * <b>Be aware that all leading and trailing whitespaces of keys and values
1403: * will be removed!</b>
1404: * </p>
1405: *
1406: * @param str The string that contains the list of key-value pairs
1407: * @param elementSeparator The separator between the elements of the list
1408: *
1409: * @return
1410: */
1411: public Map asMap(String str, String elementSeparator) {
1412: return this .toMap(str, elementSeparator, null, null);
1413: }
1414:
1415: // asMap()
1416: // -------------------------------------------------------------------------
1417:
1418: /**
1419: * Returns a new map object that contains all key-value pairs of the
1420: * specified string.
1421: *
1422: * <p>
1423: * <b>Be aware that all leading and trailing whitespaces of keys and values
1424: * will be removed!</b>
1425: * </p>
1426: *
1427: * @param str The string that contains the list of key-value pairs
1428: * @param elementSeparator The separator between the elements of the list
1429: * @param keyValueSeparator The separator between the keys and values
1430: *
1431: * @return
1432: */
1433: public Map asMap(String str, String elementSeparator,
1434: String keyValueSeparator) {
1435: return this .toMap(str, elementSeparator, keyValueSeparator,
1436: null);
1437: }
1438:
1439: // asMap()
1440: // -------------------------------------------------------------------------
1441:
1442: /**
1443: * Returns the given map object with all key-value pairs of the specified
1444: * string added to it. <br>
1445: * The separator between the keys and values is assumed to be "=".
1446: *
1447: * <p>
1448: * <b>Be aware that all leading and trailing whitespaces of keys and values
1449: * will be removed!</b>
1450: * </p>
1451: *
1452: * @param str The string that contains the list of key-value pairs
1453: * @param elementSeparator The separator between the elements of the list
1454: * @param map The map to which the key-value pairs are added
1455: *
1456: * @return
1457: */
1458: public Map toMap(String str, String elementSeparator, Map map) {
1459: return this .toMap(str, elementSeparator, null, map);
1460: }
1461:
1462: // toMap()
1463: // -------------------------------------------------------------------------
1464:
1465: /**
1466: * Adds all key-value pairs of the given string to the specified map. <br>
1467: * The separator between the elements is assumed to be "," and "=" between
1468: * key and value.
1469: *
1470: * <p>
1471: * <b>Be aware that all leading and trailing whitespaces of keys and values
1472: * will be removed!</b>
1473: * </p>
1474: *
1475: * @param str The string that contains the list of key-value pairs
1476: * @param map The map to which the key-value pairs are added
1477: *
1478: * @return
1479: */
1480: public Map toMap(String str, Map map) {
1481: return this .toMap(str, null, null, map);
1482: }
1483:
1484: // toMap()
1485: // -------------------------------------------------------------------------
1486:
1487: /**
1488: * Adds all key-value pairs of the given string to a new properties object. <br>
1489: * The separator between the elements is assumed to be "," and "=" between
1490: * key and value.
1491: *
1492: * <p>
1493: * <b>Be aware that all leading and trailing whitespaces of keys and values
1494: * will be removed!</b>
1495: * </p>
1496: *
1497: * @param str The string that contains the list of key-value pairs
1498: *
1499: * @return
1500: */
1501: public Properties asProperties(String str) {
1502: return this .toProperties(str, null);
1503: }
1504:
1505: // asProperties()
1506: // -------------------------------------------------------------------------
1507:
1508: /**
1509: * Adds all key-value pairs of the given string to the specified
1510: * properties. <br>
1511: * The separator between the elements is assumed to be "," and "=" between
1512: * key and value.
1513: *
1514: * <p>
1515: * <b>Be aware that all leading and trailing whitespaces of keys and values
1516: * will be removed!</b>
1517: * </p>
1518: *
1519: * @param str The string that contains the list of key-value pairs
1520: * @param properties The properties where the key-value pairs should be
1521: * added
1522: *
1523: * @return
1524: */
1525: public Properties toProperties(String str, Properties properties) {
1526: Properties props = (properties == null) ? new Properties()
1527: : properties;
1528:
1529: return (Properties) this .toMap(str, null, null, props);
1530: }
1531:
1532: // toProperties()
1533: // -------------------------------------------------------------------------
1534: // =========================================================================
1535: // PROTECTED INSTANCE METHODS
1536: // =========================================================================
1537:
1538: /**
1539: * Cuts off all leading and trailing occurences of separator in text.
1540: *
1541: * @param text
1542: * @param separator
1543: *
1544: * @return
1545: */
1546: protected String trimSeparator(String text, String separator) {
1547: int sepLen = separator.length();
1548:
1549: while (text.startsWith(separator)) {
1550: text = text.substring(separator.length());
1551: }
1552:
1553: while (text.endsWith(separator)) {
1554: text = text.substring(0, text.length() - sepLen);
1555: }
1556:
1557: return text;
1558: }
1559:
1560: // trimSeparator()
1561: // -------------------------------------------------------------------------
1562:
1563: /**
1564: * Returns an array of substrings of the given text. <br>
1565: * The separators between the substrings are the given delimiters. Each
1566: * character in the delimiter string is treated as a separator.
1567: *
1568: * @param text The string that should be splitted into substrings
1569: * @param delimiters All characters that should be recognized as a
1570: * separator or substrings
1571: * @param all If true, empty elements will be returned, otherwise thye are
1572: * skipped
1573: *
1574: * @return An array of substrings of the given text
1575: */
1576: protected String[] parts(String text, String delimiters, boolean all) {
1577: ArrayList result = null;
1578: StringTokenizer tokenizer = null;
1579:
1580: if (text == null) {
1581: return null;
1582: }
1583:
1584: if ((delimiters == null) || (delimiters.length() == 0)) {
1585: String[] resultArray = { text };
1586:
1587: return resultArray;
1588: }
1589:
1590: if (text.length() == 0) {
1591: return new String[0];
1592: } else {
1593: result = new ArrayList();
1594: tokenizer = new StringTokenizer(text, delimiters, all);
1595:
1596: if (all) {
1597: this .collectParts(result, tokenizer, delimiters);
1598: } else {
1599: this .collectParts(result, tokenizer);
1600: }
1601: }
1602:
1603: return (String[]) result.toArray(new String[0]);
1604: }
1605:
1606: // parts()
1607: // -------------------------------------------------------------------------
1608: protected void collectParts(List list, StringTokenizer tokenizer) {
1609: while (tokenizer.hasMoreTokens()) {
1610: list.add(tokenizer.nextToken());
1611: }
1612: }
1613:
1614: // collectParts()
1615: // -------------------------------------------------------------------------
1616: protected void collectParts(List list, StringTokenizer tokenizer,
1617: String delimiter) {
1618: String token;
1619: boolean lastWasDelimiter = false;
1620:
1621: while (tokenizer.hasMoreTokens()) {
1622: token = tokenizer.nextToken();
1623:
1624: if (delimiter.indexOf(token) >= 0) {
1625: if (lastWasDelimiter) {
1626: list.add("");
1627: }
1628:
1629: lastWasDelimiter = true;
1630: } else {
1631: list.add(token);
1632: lastWasDelimiter = false;
1633: }
1634: }
1635: }
1636:
1637: // collectParts()
1638: // -------------------------------------------------------------------------
1639:
1640: /**
1641: * Returns the given text split up into an array of strings, at the
1642: * occurrances of the separator string. In contrary to method parts() the
1643: * separator is a one or many character sequence delimiter. That is, only
1644: * the exact sequence of the characters in separator identifies the end
1645: * of a substring. Parameter all defines whether empty strings between
1646: * consecutive separators are added to the result or not.
1647: *
1648: * @param text The text to be split up
1649: * @param separator The string that separates the substrings
1650: * @param all If true, empty strings are added, otherwise skipped
1651: *
1652: * @return An array of substrings not containing any separator anymore
1653: *
1654: * @see #parts(String, String, boolean)
1655: */
1656: protected String[] substrings(String text, String separator,
1657: boolean all) {
1658: int index = 0;
1659: int start = 0;
1660: int sepLen = 0;
1661: int strLen = 0;
1662: String str = text;
1663: ArrayList strings = new ArrayList();
1664:
1665: if (text == null) {
1666: return new String[0];
1667: }
1668:
1669: if ((separator == null) || (separator.length() == 0)) {
1670: if (text.length() == 0) {
1671: return new String[0];
1672: }
1673:
1674: String[] resultArray = { text };
1675:
1676: return resultArray;
1677: }
1678:
1679: if (!all) {
1680: str = this .trimSeparator(text, separator);
1681: }
1682:
1683: strLen = str.length();
1684:
1685: if (strLen > 0) {
1686: sepLen = separator.length();
1687: index = str.indexOf(separator, start);
1688:
1689: while (index >= 0) {
1690: if (all) {
1691: if (index > 0) {
1692: strings.add(str.substring(start, index));
1693: }
1694: } else {
1695: if (index > (start + sepLen)) {
1696: strings.add(str.substring(start, index));
1697: }
1698: }
1699:
1700: start = index + sepLen;
1701: index = str.indexOf(separator, start);
1702: }
1703:
1704: if (start < strLen) {
1705: strings.add(str.substring(start));
1706: }
1707: }
1708:
1709: return (String[]) strings.toArray(new String[0]);
1710: }
1711:
1712: // substrings()
1713: // -------------------------------------------------------------------------
1714: protected String padCh(String str, int len, char ch, boolean left) {
1715: StringBuffer buffer = null;
1716: int missing = len - str.length();
1717:
1718: if (missing <= 0) {
1719: return str;
1720: }
1721:
1722: buffer = new StringBuffer(len);
1723:
1724: if (!left) {
1725: buffer.append(str);
1726: }
1727:
1728: for (int i = 1; i <= missing; i++) {
1729: buffer.append(ch);
1730: }
1731:
1732: if (left) {
1733: buffer.append(str);
1734: }
1735:
1736: return buffer.toString();
1737: }
1738:
1739: // padCh()
1740: // -------------------------------------------------------------------------
1741: protected int indexOfString(String[] strArray, String searchStr,
1742: boolean ignoreCase) {
1743: if ((strArray == null) || (strArray.length == 0)) {
1744: return -1;
1745: }
1746:
1747: boolean found = false;
1748:
1749: for (int i = 0; i < strArray.length; i++) {
1750: if (strArray[i] == null) {
1751: if (searchStr == null) {
1752: found = true;
1753: }
1754: } else {
1755: if (ignoreCase) {
1756: found = strArray[i].equalsIgnoreCase(searchStr);
1757: } else {
1758: found = strArray[i].equals(searchStr);
1759: }
1760: }
1761:
1762: if (found) {
1763: return i;
1764: }
1765: }
1766:
1767: return -1;
1768: }
1769:
1770: // indexOfString()
1771: // -------------------------------------------------------------------------
1772:
1773: /**
1774: * Returns the substring of the given string that comes before the first
1775: * occurance of the specified separator. If the string starts with a
1776: * separator, the result will be an empty string. If the string doesn't
1777: * contain the separator the method returns null or the whole string,
1778: * depending on the returnNull flag.
1779: *
1780: * @param str The string of which the prefix is desired
1781: * @param separator Separates the prefix from the rest of the string
1782: * @param returnNull Specifies if null will be returned if no separator is
1783: * found
1784: *
1785: * @return
1786: */
1787: protected String prefix(String str, String separator,
1788: boolean returnNull) {
1789: if (str == null) {
1790: return null;
1791: }
1792:
1793: if (separator == null) {
1794: return (returnNull ? null : str);
1795: }
1796:
1797: int index = str.indexOf(separator);
1798:
1799: if (index >= 0) {
1800: return str.substring(0, index);
1801: } else {
1802: return (returnNull ? null : str);
1803: }
1804: }
1805:
1806: // prefix()
1807: // -------------------------------------------------------------------------
1808:
1809: /**
1810: * Returns the substring of the given string that comes after the first
1811: * occurance of the specified separator. If the string ends with a
1812: * separator, the result will be an empty string. If the string doesn't
1813: * contain the separator the method returns null or the whole string,
1814: * depending on the returnNull flag.
1815: *
1816: * @param str The string of which the suffix is desired
1817: * @param separator Separates the suffix from the rest of the string
1818: * @param returnNull Specifies if null will be returned if no separator is
1819: * found
1820: *
1821: * @return
1822: */
1823: protected String suffix(String str, String separator,
1824: boolean returnNull) {
1825: if (str == null) {
1826: return null;
1827: }
1828:
1829: if (separator == null) {
1830: return (returnNull ? null : str);
1831: }
1832:
1833: int index = str.indexOf(separator);
1834:
1835: if (index >= 0) {
1836: return str.substring(index + separator.length());
1837: } else {
1838: return (returnNull ? null : str);
1839: }
1840: }
1841:
1842: // suffix()
1843: // -------------------------------------------------------------------------
1844:
1845: /**
1846: * Removes the given strings from the array. If removeStrings is null it
1847: * means that all null values are removed from the first array.
1848: *
1849: * @param strings
1850: * @param removeStrings
1851: *
1852: * @return
1853: */
1854: protected String[] removeFromStringArray(String[] strings,
1855: String[] removeStrings) {
1856: List list;
1857: boolean remains;
1858: list = new ArrayList(strings.length);
1859:
1860: for (int i = 0; i < strings.length; i++) {
1861: if (removeStrings == null) {
1862: remains = strings[i] != null;
1863: } else {
1864: remains = !this .contains(removeStrings, strings[i]);
1865: }
1866:
1867: if (remains) {
1868: list.add(strings[i]);
1869: }
1870: }
1871:
1872: return (String[]) list.toArray(new String[list.size()]);
1873: }
1874:
1875: // removeFromStringArray()
1876: // -------------------------------------------------------------------------
1877: }
1878:
1879: // class StringUtil
|