]>
cygwin.com Git - cygwin-apps/setup.git/blob - String++.cc
2 * Copyright (c) 2002, Robert Collins.
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; either version 2 of the License, or
7 * (at your option) any later version.
9 * A copy of the GNU General Public License can be found at
12 * Written by Robert Collins.
16 // A String class to replace all the char * manipulation.
21 #include "io_stream.h"
30 String::_data::_data(_data
const &aData
) : count (1), theString (new unsigned char[aData
.length
]), cstr(0), length (aData
.length
) {
31 memcpy (theString
, aData
.theString
, aData
.length
);
34 String::_data::_data(): count (1), theString(new unsigned char[0]), cstr (0), length (0) {}
35 String::_data::_data(size_t aLength
): count (1), theString(new unsigned char[aLength
]), cstr(0), length (aLength
) {}
36 String::_data::~_data ()
46 String::String (const char *acString
) : theData (new _data(acString
? strlen(acString
) : 0))
48 memcpy (theData
->theString
, acString
, theData
->length
);
53 if (--theData
->count
== 0)
57 String::String (int const anInt
)
61 theData
= new _data(os
.str().size());
62 memcpy (theData
->theString
, os
.str().c_str(), os
.str().size());
65 String::String (string
const &aString
) : theData (new _data (aString
.c_str() ? strlen (aString
.c_str()) : 0))
67 memcpy (theData
->theString
, aString
.c_str(), theData
->length
);
70 // able to cache the result if needed.
74 if (theData
->length
== 0)
76 char * tempcStr
=new char[theData
->length
+ 1];
77 // remove when exceptions are done
80 tempcStr
[theData
->length
] = '\0';
81 memcpy (tempcStr
, theData
->theString
, theData
->length
);
88 if (theData
->length
== 0)
90 char * tempcStr
=new char[theData
->length
+ 1];
91 // remove when exceptions are done
94 tempcStr
[theData
->length
] = '\0';
95 memcpy (tempcStr
, theData
->theString
, theData
->length
);
99 // able to cache the result if needed.
101 String::cstr_oneuse () const
103 if (theData
->length
== 0)
106 delete[] theData
->cstr
;
107 theData
->cstr
= new char[theData
->length
+ 1];
108 theData
->cstr
[theData
->length
] = '\0';
109 memcpy (theData
->cstr
, theData
->theString
, theData
->length
);
110 return theData
->cstr
;
113 // does this character exist in the string?
114 // 0 is false, 1 is the first position...
115 // XXX FIXME: Introduce npos, and change all
116 // if (size) calls to be if (size()==npos)
118 String::find(char aChar
) const
120 for (size_t i
=0; i
< theData
->length
; ++i
)
121 if (theData
->theString
[i
] == aChar
)
127 String::substr(size_t start
, size_t len
) const
129 // Adapt the C++ string class
130 return string(cstr_oneuse()).substr(start
, len
);
134 String::compare (String
const &aString
, size_t const count
) const
137 if (theData
== aString
.theData
)
139 size_t length
= count
? count
: theData
->length
;
140 if (length
> theData
->length
)
141 length
= theData
->length
;
142 if (length
> aString
.theData
->length
)
143 length
= aString
.theData
->length
;
145 for (i
=0; i
< length
; ++i
)
146 if (theData
->theString
[i
] < aString
.theData
->theString
[i
])
148 else if (theData
->theString
[i
] > aString
.theData
->theString
[i
])
151 if (i
== count
&& count
!= 0)
153 if (theData
->length
< aString
.theData
->length
)
155 else if (theData
->length
> aString
.theData
->length
)
161 String::casecompare (String
const &aString
, size_t const count
) const
164 if (theData
== aString
.theData
)
166 size_t length
= count
? count
: theData
->length
;
167 if (length
> theData
->length
)
168 length
= theData
->length
;
169 if (length
> aString
.theData
->length
)
170 length
= aString
.theData
->length
;
172 for (i
=0; i
< length
; ++i
)
173 if (toupper(theData
->theString
[i
]) < toupper(aString
.theData
->theString
[i
]))
175 else if (toupper(theData
->theString
[i
]) > toupper(aString
.theData
->theString
[i
]))
178 if (i
== count
&& count
!= 0)
180 if (theData
->length
< aString
.theData
->length
)
182 else if (theData
->length
> aString
.theData
->length
)
188 String::operator+= (String
const &aString
)
190 if (theData
->count
> 1)
192 _data
* someData
= new _data(*theData
);
197 unsigned char *tempString
= theData
->theString
;
198 theData
->theString
= new unsigned char [theData
->length
+ aString
.theData
->length
];
199 // remove when exceptions are done
200 if (!theData
->theString
)
202 memcpy (theData
->theString
, tempString
, theData
->length
);
204 memcpy (&theData
->theString
[theData
->length
], aString
.theData
->theString
, aString
.theData
->length
);
205 theData
->length
+= aString
.theData
->length
;
210 String::operator + (String
const &aString
) const
212 unsigned char *tempcString
= new unsigned char [theData
->length
+ aString
.theData
->length
];
213 // remove when exceptions are done
216 memcpy (tempcString
, theData
->theString
, theData
->length
);
217 memcpy (&tempcString
[theData
->length
], aString
.theData
->theString
, aString
.theData
->length
);
218 return absorb (tempcString
, theData
->length
+ aString
.theData
->length
);
222 String::operator + (char const *aString
) const
224 // expensive, but quick to code.
225 return *this + String (aString
);
229 String::operator == (String
const &rhs
) const
231 return compare (rhs
) ? false : true;
235 String::operator == (char const *rhs
) const
237 return compare (rhs
) ? false : true;
241 String::absorb (unsigned char *aString
, size_t aLength
)
244 theString
.theData
->theString
= aString
;
245 theString
.theData
->length
= aLength
;
250 String::casecompare (String
const lhs
, String
const rhs
)
252 return lhs
.casecompare (rhs
);
255 /* TODO: research how wide char and unicode interoperate with
259 operator << (ostream
&os
, String
const &theString
)
261 os
<< theString
.cstr_oneuse();
This page took 0.051949 seconds and 6 git commands to generate.