001: package org.incava.lang;
002:
003: import java.util.*;
004:
005: /**
006: * Extensions to the String class.
007: */
008: public class StringExt {
009: /**
010: * Set this to true for debugging output.
011: */
012: public static boolean DEBUG = false;
013:
014: /**
015: * Returns an array of strings split at the character delimiter.
016: */
017: public static String[] split(String str, char delim, int max) {
018: return split(str, "" + delim, max);
019: }
020:
021: /**
022: * Returns an array of strings split at the string delimiter.
023: */
024: public static String[] split(String str, String delim, int max) {
025: if (max == 1) {
026: return new String[] { str };
027: } else {
028: --max; // adjust count between 0 and 1
029: List splitList = new ArrayList();
030: int nFound = 0;
031: int strlen = str.length();
032: int end = 0;
033: int beg = 0;
034: int delimlen = delim.length();
035: for (int idx = 0; idx < strlen; ++idx) {
036: if (left(str.substring(idx), delimlen).equals(delim)) {
037: String substr = str.substring(beg, end);
038: splitList.add(substr);
039: beg = end + 1;
040: if (max > 0 && ++nFound >= max) {
041: break;
042: }
043: }
044: ++end;
045: }
046:
047: if (strlen > beg) {
048: String tmp = strlen == beg ? "" : str.substring(beg,
049: strlen);
050: splitList.add(tmp);
051: }
052:
053: if (DEBUG) {
054: System.out.println("split(" + str + ", " + delim + ", "
055: + max + "):");
056: for (int i = 0; i < splitList.size(); ++i) {
057: System.out.println(" [" + i + "] = '"
058: + splitList.get(i) + "'");
059: }
060: }
061:
062: return (String[]) splitList.toArray(new String[0]);
063: }
064: }
065:
066: /**
067: * Returns an array of strings split at the character delimiter.
068: */
069: public static String[] split(String str, char delim) {
070: return split(str, "" + delim, -1);
071: }
072:
073: /**
074: * Returns an array of strings split at the string delimiter.
075: */
076: public static String[] split(String str, String delim) {
077: return split(str, delim, -1);
078: }
079:
080: /**
081: * Converts the (possibly quoted) string into a list, delimited by
082: * whitespace and commas..
083: */
084: public static List listify(String str) {
085: // strip leading/trailing single/double quotes
086: if (str.charAt(0) == str.charAt(str.length() - 1)
087: && (str.charAt(0) == '"' || str.charAt(0) == '\'')) {
088: str = str.substring(1, str.length() - 1);
089: }
090:
091: List list = new ArrayList();
092: StringTokenizer st = new StringTokenizer(str, " \t\n\r\f,");
093: while (st.hasMoreTokens()) {
094: String tk = st.nextToken();
095: list.add(tk);
096: }
097: return list;
098: }
099:
100: /**
101: * Returns a string starting with the <code>str</code> parameter, with
102: * <code>ch</code>'s following the string to a length of
103: * <code>length</code>.
104: *
105: * Examples:
106: * pad("abcd", '*', 8) -> "abcd****"
107: * pad("abcd", '*', 3) -> "abcd"
108: */
109: public static String pad(String str, char ch, int length) {
110: StringBuffer buf = new StringBuffer(str);
111: while (buf.length() < length) {
112: buf.append(ch);
113: }
114: return buf.toString();
115: }
116:
117: /**
118: * Same as the <code>pad</code> method, but applies the padding to the
119: * left-hand (leading) side of the string.
120: *
121: * Examples:
122: * <pre>
123: * pad("420", '*', 8) -> "*****420"
124: * pad("1144", '*', 3) -> "1144"
125: * </pre>
126: */
127: public static String padLeft(String str, char ch, int length) {
128: return repeat(ch, length - str.length()) + str;
129: }
130:
131: public static String pad(String str, int length) {
132: return pad(str, ' ', length);
133: }
134:
135: public static String repeat(String str, int length) {
136: StringBuffer buf = new StringBuffer();
137: for (int i = 0; i < length; ++i) {
138: buf.append(str);
139: }
140: return buf.toString();
141: }
142:
143: public static String repeat(char ch, int length) {
144: StringBuffer buf = new StringBuffer();
145: for (int i = 0; i < length; ++i) {
146: buf.append(ch);
147: }
148: return buf.toString();
149: }
150:
151: public String toString(double n, int precision) {
152: String str = Double.toString(n);
153: int dot = str.indexOf('.');
154: if (dot != -1 && dot + precision < str.length()) {
155: str = str.substring(0, dot + precision);
156: }
157: return str;
158: }
159:
160: /**
161: * Returns the leftmost n characters of the string, not exceeding the length
162: * of the string. Does not throw the annoying IndexOutOfBoundsException.
163: */
164: public static String left(String str, int n) {
165: int x = Math.min(n, str.length());
166: x = Math.max(0, x); // guard against 0
167: return str.substring(0, x);
168: }
169:
170: /**
171: * Returns the rightmost n characters of the string, not exceeding the
172: * length of the string. Does not throw the annoying
173: * IndexOutOfBoundsException.
174: */
175: public static String right(String str, int n) {
176: int x = Math.min(n, str.length());
177: x = Math.max(0, x); // guard against 0
178: int s = str.length() - x;
179: return str.substring(s);
180: }
181:
182: public static String join(Collection c, String str) {
183: StringBuffer buf = new StringBuffer();
184: boolean isFirst = true;
185: Iterator it = c.iterator();
186: while (it.hasNext()) {
187: if (!isFirst) {
188: buf.append(str);
189: } else {
190: isFirst = false;
191: }
192: buf.append(it.next());
193: }
194: return buf.toString();
195: }
196:
197: public static void test(String str, char del) {
198: System.out.println("----- test: \"" + str + "\" -----");
199: String[] splits = StringExt.split(str, del);
200: System.out.println("#splits: " + splits.length);
201: for (int i = 0; i < splits.length; ++i) {
202: System.out.println(" # " + i + ": " + splits[i]);
203: }
204: }
205:
206: public static void test(String str, String del) {
207: System.out.println("----- test: \"" + str + "\" -----");
208: String[] splits = StringExt.split(str, del);
209: System.out.println("#splits: " + splits.length);
210: for (int i = 0; i < splits.length; ++i) {
211: System.out.println(" # " + i + ": " + splits[i]);
212: }
213: }
214:
215: public static void main(String[] args) {
216: test("this;is;a;test", ';');
217: test(";is;a;test", ';');
218: test("this;is;a;", ';');
219: test("this;;a;test", ';');
220: test(";this;;a;test;;", ';');
221: test("this is yet another test, it is.", "is");
222: }
223: }
|