changes.
[IRC.git] / Robust / src / ClassLibrary / SSJava / String.java
1 import Vector;
2
3 @LATTICE("V<C, V<O")
4 @METHODDEFAULT("O<V,V<C,C<IN,C*,THISLOC=O,RETURNLOC=O")
5 public class String {
6
7   @LOC("V")
8   char value[];
9
10   @LOC("C")
11   int count;
12
13   @LOC("O")
14   int offset;
15
16   @LOC("V")
17   private int cachedHashcode;
18
19   private String() {
20   }
21
22   public String(char c) {
23     char[] str = new char[1];
24     str[0] = c;
25     String(str);
26   }
27
28   public String(char str[]) {
29     char charstr[] = new char[str.length];
30     for (int i = 0; i < str.length; i++)
31       charstr[i] = str[i];
32     this.value = charstr;
33     this.count = str.length;
34     this.offset = 0;
35   }
36
37   public String(byte str[]) {
38     char charstr[] = new char[str.length];
39     for (int i = 0; i < str.length; i++)
40       charstr[i] = (char) str[i];
41     this.value = charstr;
42     this.count = str.length;
43     this.offset = 0;
44   }
45
46   public String(byte str[], int offset, int length) {
47     if (length > (str.length - offset))
48       length = str.length - offset;
49     char charstr[] = new char[length];
50     for (int i = 0; i < length; i++)
51       charstr[i] = (char) str[i + offset];
52     this.value = charstr;
53     this.count = length;
54     this.offset = 0;
55   }
56
57   public String(byte str[], String encoding) {
58     int length = this.count;
59     if (length > (str.length))
60       length = str.length;
61     char charstr[] = new char[length];
62     for (int i = 0; i < length; i++)
63       charstr[i] = (char) str[i];
64     this.value = charstr;
65     this.count = length;
66     this.offset = 0;
67   }
68
69   public String(char str[], int offset, int length) {
70     if (length > (str.length - offset))
71       length = str.length - offset;
72     char charstr[] = new char[length];
73     for (int i = 0; i < length; i++)
74       charstr[i] = str[i + offset];
75     this.value = charstr;
76     this.count = length;
77     this.offset = 0;
78   }
79
80   public String(String str) {
81     this.value = str.value;
82     this.count = str.count;
83     this.offset = str.offset;
84   }
85
86   public String(StringBuffer strbuf) {
87     value = new char[strbuf.length()];
88     count = strbuf.length();
89     offset = 0;
90     for (int i = 0; i < count; i++)
91       value[i] = strbuf.value[i];
92   }
93
94   public boolean endsWith(String suffix) {
95     return regionMatches(count - suffix.count, suffix, 0, suffix.count);
96   }
97
98   public String substring(int beginIndex) {
99     return substring(beginIndex, this.count);
100   }
101
102   public String subString(int beginIndex, int endIndex) {
103     return substring(beginIndex, endIndex);
104   }
105
106   public String substring(int beginIndex, int endIndex) {
107     String str = new String();
108     if (beginIndex > this.count || endIndex > this.count || beginIndex > endIndex) {
109       // FIXME
110       System.printString("Index error: " + beginIndex + " " + endIndex + " " + count + "\n" + this);
111     }
112     str.value = this.value;
113     str.count = endIndex - beginIndex;
114     str.offset = this.offset + beginIndex;
115     return str;
116   }
117
118   public String subString(int beginIndex) {
119     return this.subString(beginIndex, this.count);
120   }
121
122   public int lastindexOf(int ch) {
123     return this.lastindexOf(ch, count - 1);
124   }
125
126   public int lastIndexOf(char ch) {
127     return this.lastindexOf((int) ch, count - 1);
128   }
129
130   public static String concat2(String s1, String s2) {
131     if (s1 == null)
132       return "null".concat(s2);
133     else
134       return s1.concat(s2);
135   }
136
137   public String concat(String str) {
138     String newstr = new String();
139     newstr.count = this.count + str.count;
140     char charstr[] = new char[newstr.count];
141     newstr.offset = 0;
142     for (int i = 0; i < count; i++) {
143       charstr[i] = value[i + offset];
144     }
145     for (int i = 0; i < str.count; i++) {
146       charstr[i + count] = str.value[i + str.offset];
147     }
148     newstr.value = charstr;
149     return newstr;
150   }
151
152   public int lastindexOf(int ch, int fromIndex) {
153     for (int i = fromIndex; i > 0; i--)
154       if (this.charAt(i) == ch)
155         return i;
156     return -1;
157   }
158
159   public String replace(char oldch, char newch) {
160     char[] buffer = new char[count];
161     for (int i = 0; i < count; i++) {
162       char x = charAt(i);
163       if (x == oldch)
164         x = newch;
165       buffer[i] = x;
166     }
167     return new String(buffer);
168   }
169
170   public String toUpperCase() {
171     char[] buffer = new char[count];
172     for (int i = 0; i < count; i++) {
173       char x = charAt(i);
174       if (x >= 'a' && x <= 'z') {
175         x = (char) ((x - 'a') + 'A');
176       }
177       buffer[i] = x;
178     }
179     return new String(buffer);
180   }
181
182   public String toLowerCase() {
183     char[] buffer = new char[count];
184     for (int i = 0; i < count; i++) {
185       char x = charAt(i);
186       if (x >= 'A' && x <= 'Z') {
187         x = (char) ((x - 'A') + 'a');
188       }
189       buffer[i] = x;
190     }
191     return new String(buffer);
192   }
193
194   public int indexOf(int ch) {
195     return this.indexOf(ch, 0);
196   }
197
198   public int indexOf(int ch, int fromIndex) {
199     for (int i = fromIndex; i < count; i++)
200       if (this.charAt(i) == ch)
201         return i;
202     return -1;
203   }
204
205   public int indexOf(String str) {
206     return this.indexOf(str, 0);
207   }
208
209   public int indexOf(String str, int fromIndex) {
210     if (fromIndex < 0)
211       fromIndex = 0;
212     for (int i = fromIndex; i <= (count - str.count); i++)
213       if (regionMatches(i, str, 0, str.count))
214         return i;
215     return -1;
216   }
217
218   public int indexOfIgnoreCase(String str, int fromIndex) {
219     if (fromIndex < 0)
220       fromIndex = 0;
221   }
222
223   public int lastIndexOf(String str, int fromIndex) {
224     int k = count - str.count;
225     if (k > fromIndex)
226       k = fromIndex;
227     for (; k >= 0; k--) {
228       if (regionMatches(k, str, 0, str.count))
229         return k;
230     }
231     return -1;
232   }
233
234   public int lastIndexOf(String str) {
235     return lastIndexOf(str, count - str.count);
236   }
237
238   public boolean startsWith(String str) {
239     return regionMatches(0, str, 0, str.count);
240   }
241
242   public boolean startsWith(String str, int toffset) {
243     return regionMatches(toffset, str, 0, str.count);
244   }
245
246   public boolean regionMatches(int toffset, String other, int ooffset, int len) {
247     if (toffset < 0 || ooffset < 0 || (toffset + len) > count || (ooffset + len) > other.count)
248       return false;
249     for (int i = 0; i < len; i++)
250       if (other.value[i + other.offset + ooffset] != this.value[i + this.offset + toffset])
251         return false;
252     return true;
253   }
254
255   public char[] toCharArray() {
256     char str[] = new char[count];
257     for (int i = 0; i < count; i++)
258       str[i] = value[i + offset];
259     return str;
260   }
261
262   public byte[] getBytes() {
263     byte str[] = new byte[count];
264     for (int i = 0; i < count; i++)
265       str[i] = (byte) value[i + offset];
266     return str;
267   }
268
269   public void getChars(char dst[], int dstBegin) {
270     getChars(0, count, dst, dstBegin);
271   }
272
273   public void getChars(int srcBegin, int srcEnd, char dst[], int dstBegin) {
274     if ((srcBegin < 0) || (srcEnd > count) || (srcBegin > srcEnd)) {
275       // FIXME
276       System.printString("Index error: " + srcBegin + " " + srcEnd + " " + count + "\n" + this);
277       System.exit(-1);
278     }
279     int len = srcEnd - srcBegin;
280     int j = dstBegin;
281     for (int i = srcBegin; i < srcEnd; i++)
282       dst[j++] = value[i + offset];
283     return;
284   }
285
286   public int length() {
287     return count;
288   }
289
290   public char charAt(int i) {
291     return value[i + offset];
292   }
293
294   public String toString() {
295     return this;
296   }
297
298   public static String valueOf(@LOC("IN") Object o) {
299     if (o == null)
300       return "null";
301     else
302       return o.toString();
303   }
304
305   public static String valueOf(boolean b) {
306     if (b)
307       return new String("true");
308     else
309       return new String("false");
310   }
311
312   public static String valueOf(@LOC("IN") char c) {
313     @LOC("C") char ar[] = new char[1];
314     ar[0] = c;
315     return new String(ar);
316   }
317
318   public static String valueOf(@LOC("IN") int x) {
319     @LOC("C") int length = 0;
320     @LOC("C") int tmp;
321     if (x < 0)
322       tmp = -x;
323     else
324       tmp = x;
325     do {
326       tmp = tmp / 10;
327       length = length + 1;
328     } while (tmp != 0);
329
330     @LOC("C") char chararray[];
331     if (x < 0)
332       chararray = new char[length + 1];
333     else
334       chararray = new char[length];
335     @LOC("C") int voffset;
336     if (x < 0) {
337       chararray[0] = '-';
338       voffset = 1;
339       x = -x;
340     } else
341       voffset = 0;
342
343     do {
344       chararray[--length + voffset] = (char) (x % 10 + '0');
345       x = x / 10;
346     } while (length != 0);
347     return new String(chararray);
348   }
349
350   public static String valueOf(double val) {
351     char[] chararray = new char[20];
352     String s = new String();
353     s.offset = 0;
354     s.count = convertdoubletochar(val, chararray);
355     s.value = chararray;
356     return s;
357   }
358
359   public static native int convertdoubletochar(double val, char[] chararray);
360
361   public static String valueOf(@LOC("IN") long x) {
362     @LOC("C") int length = 0;
363     @LOC("C") long tmp;
364     if (x < 0)
365       tmp = -x;
366     else
367       tmp = x;
368     do {
369       tmp = tmp / 10;
370       length = length + 1;
371     } while (tmp != 0);
372
373     @LOC("C") char chararray[];
374     if (x < 0)
375       chararray = new char[length + 1];
376     else
377       chararray = new char[length];
378     @LOC("C") int voffset;
379     if (x < 0) {
380       chararray[0] = '-';
381       voffset = 1;
382       x = -x;
383     } else
384       voffset = 0;
385
386     do {
387       chararray[--length + voffset] = (char) (x % 10 + '0');
388       x = x / 10;
389     } while (length != 0);
390     return new String(chararray);
391   }
392
393   public int compareTo(String s) {
394     int smallerlength = count < s.count ? count : s.count;
395
396     for (int i = 0; i < smallerlength; i++) {
397       int valDiff = this.charAt(i) - s.charAt(i);
398       if (valDiff != 0) {
399         return valDiff;
400       }
401     }
402     return count - s.count;
403   }
404
405   public int hashCode() {
406     if (cachedHashcode != 0)
407       return cachedHashcode;
408     @LOC("C") int hashcode = 0;
409     for (@LOC("C") int i = 0; i < count; i++)
410       hashcode = hashcode * 31 + value[i + offset];
411     cachedHashcode = hashcode;
412     return hashcode;
413   }
414
415   public boolean equals(Object o) {
416     if (o.getType() != getType())
417       return false;
418     String s = (String) o;
419     if (s.count != count)
420       return false;
421     for (int i = 0; i < count; i++) {
422       if (s.value[i + s.offset] != value[i + offset])
423         return false;
424     }
425     return true;
426   }
427
428   public boolean equalsIgnoreCase(String s) {
429     if (s.count != count)
430       return false;
431     for (int i = 0; i < count; i++) {
432       char l = s.value[i + s.offset];
433       char r = value[i + offset];
434       if (l >= 'a' && l <= 'z')
435         l = (char) ((l - 'a') + 'A');
436       if (r >= 'a' && r <= 'z')
437         r = (char) ((r - 'a') + 'A');
438       if (l != r)
439         return false;
440     }
441     return true;
442   }
443
444   public Vector split() {
445     Vector splitted = new Vector();
446     int i;
447     int cnt = 0;
448
449     // skip first spaces
450     for (i = 0; i < count; i++) {
451       if (value[i + offset] != '\n' && value[i + offset] != '\t' && value[i + offset] != ' ')
452         break;
453     }
454
455     int oldi = i;
456
457     while (i < count) {
458       if (value[i + offset] == '\n' || value[i + offset] == '\t' || value[i + offset] == ' ') {
459         String t = new String();
460         t.value = value;
461         t.offset = oldi;
462         t.count = i - oldi;
463         splitted.addElement(t);
464
465         // skip extra spaces
466         while (i < count
467             && (value[i + offset] == '\n' || value[i + offset] == '\t' || value[i + offset] == ' ')) {
468           i++;
469         }
470         oldi = i;
471       } else {
472         i++;
473       }
474     }
475
476     if (i != oldi) {
477       String t = new String();
478       t.value = value;
479       t.offset = oldi;
480       t.count = i - oldi;
481       splitted.addElement(t);
482     }
483
484     return splitted;
485   }
486
487   public boolean contains(String str) {
488     int i, j;
489     char[] strChar = str.toCharArray();
490     int cnt;
491
492     for (i = 0; i < count; i++) {
493       if (value[i] == strChar[0]) {
494         cnt = 0;
495         for (j = 0; j < str.length() && i + j < count; j++) {
496           if (value[i + j] == strChar[j])
497             cnt++;
498         }
499         if (cnt == str.length())
500           return true;
501       }
502     }
503
504     return false;
505
506   }
507
508   public String trim() {
509     int len = count;
510     int st = 0;
511     int off = offset; /* avoid getfield opcode */
512     char[] val = value; /* avoid getfield opcode */
513
514     while ((st < len) && (val[off + st] <= ' ')) {
515       st++;
516     }
517     while ((st < len) && (val[off + len - 1] <= ' ')) {
518       len--;
519     }
520     return ((st > 0) || (len < count)) ? substring(st, len) : this;
521   }
522
523   public boolean matches(String regex) {
524     System.println("String.matches() is not fully supported");
525     return this.equals(regex);
526   }
527 }