Commit | Line | Data |
---|---|---|
d44e3c4f | 1 | /****************************************************************************** |
2 | * Copyright (c) 2000-2016 Ericsson Telecom AB | |
3 | * All rights reserved. This program and the accompanying materials | |
4 | * are made available under the terms of the Eclipse Public License v1.0 | |
5 | * which accompanies this distribution, and is available at | |
6 | * http://www.eclipse.org/legal/epl-v10.html | |
7 | * | |
8 | * Contributors: | |
9 | * Balasko, Jeno | |
10 | * Cserveni, Akos | |
11 | * Forstner, Matyas | |
12 | * Gecse, Roland | |
13 | * Kremer, Peter | |
14 | * Raduly, Csaba | |
15 | * Szabados, Kristof | |
16 | * Szabo, Janos Zoltan – initial implementation | |
17 | * Zalanyi, Balazs Andor | |
18 | * | |
19 | ******************************************************************************/ | |
970ed795 EL |
20 | #ifndef _Common_string_HH |
21 | #define _Common_string_HH | |
22 | ||
23 | #include <string.h> | |
24 | ||
25 | class stringpool; | |
26 | class ustring; | |
27 | ||
28 | /** | |
29 | * Class for handling general string operations. | |
30 | */ | |
31 | class string { | |
32 | friend class stringpool; | |
33 | friend string operator+(const char *s1, const string& s2); | |
34 | ||
35 | /** string value structure */ | |
36 | struct string_struct { | |
37 | unsigned int ref_count; | |
38 | size_t n_chars; | |
39 | char chars_ptr[sizeof(size_t)]; | |
40 | } *val_ptr; | |
41 | ||
42 | string(size_t n) : val_ptr(0) { init_struct(n); } | |
43 | string(string_struct *ptr) : val_ptr(ptr) { val_ptr->ref_count++; } | |
44 | ||
45 | void init_struct(size_t n_chars); | |
46 | void copy_value_and_append(const char *s, size_t n); | |
47 | void replace(size_t pos, size_t n, const char *s, size_t s_len); | |
48 | static void clean_up(string_struct *ptr); | |
49 | ||
50 | /** Three-way lexicographical comparison of \a *this and \a s, | |
51 | * much like \c strcmp. */ | |
52 | int compare(const string& s) const; | |
53 | ||
54 | /** Three-way lexicographical comparison of \a *this and \a s, | |
55 | * much like \c strcmp. */ | |
56 | int compare(const char *s) const; | |
57 | ||
58 | public: | |
59 | /** The largest possible value of type size_t. That is, size_t(-1). */ | |
60 | static const size_t max_string_len = (size_t)-1 - | |
61 | (sizeof(string_struct) - sizeof(size_t) + 1); | |
62 | ||
63 | /** Constructs an empty string. */ | |
64 | string() : val_ptr(0) { init_struct(0); } | |
65 | ||
66 | /** Constructs a string containing single character \a c. */ | |
67 | explicit string(char c) : val_ptr(0) | |
68 | { init_struct(1); val_ptr->chars_ptr[0] = c; } | |
69 | ||
70 | /** Constructs a string from \a s. */ | |
71 | explicit string(const char *s); | |
72 | ||
73 | /** Constructs a string from \a s taking the first \a n characters. */ | |
74 | string(size_t n, const char *s); | |
75 | ||
76 | /** Copy constructor */ | |
77 | string(const string& s) : val_ptr(s.val_ptr) { val_ptr->ref_count++; } | |
78 | ||
79 | /** Constructs a string from ustring \a s. All characters of \a s must fit | |
80 | * in one byte. */ | |
81 | explicit string(const ustring& s); | |
82 | ||
83 | /** The destructor. */ | |
84 | ~string() { clean_up(val_ptr); } | |
85 | ||
86 | /** Returns the size of the string. */ | |
87 | size_t size() const { return val_ptr->n_chars; } | |
88 | ||
89 | /** true if the string's size is 0. */ | |
90 | bool empty() const { return val_ptr->n_chars == 0; } | |
91 | ||
92 | /** true if the string contains a valid value of TTCN-3 type charstring | |
93 | * i.e. character code of every character is within the range 0..127 */ | |
94 | bool is_cstr() const; | |
95 | ||
96 | /** Returns a pointer to a null-terminated array of characters | |
97 | * representing the string's contents. */ | |
98 | const char *c_str() const { return val_ptr->chars_ptr; } | |
99 | ||
100 | /** Erases the string; identical to \a *this="". */ | |
101 | void clear(); | |
102 | ||
103 | /** Creates a string from a substring of \a *this. | |
104 | * The substring begins at character position \a pos, | |
105 | * and terminates at character position \a pos+n or at the end of | |
106 | * the string, whichever comes first. */ | |
107 | string substr(size_t pos=0, size_t n=max_string_len) const; | |
108 | ||
109 | /** Appends characters, or erases characters from the end, | |
110 | * as necessary to make the string's length exactly \a n characters. */ | |
111 | void resize(size_t n, char c = '\0'); | |
112 | ||
113 | /** Replaces the \a n long substring of \a *this beginning | |
114 | * at position \a pos with the string \a s. */ | |
115 | void replace(size_t pos, size_t n, const string& s); | |
116 | ||
117 | /** Replaces the \a n long substring of \a *this beginning | |
118 | * at position \a pos with the string \a s. | |
119 | * @pre \a s must not be NULL */ | |
120 | void replace(size_t pos, size_t n, const char *s); | |
121 | ||
122 | /** Searches for the character \a c, beginning at character | |
123 | * position \a pos. If not found, returns size(). */ | |
124 | size_t find(char c, size_t pos=0) const; | |
125 | ||
126 | /** Searches for a null-terminated character array | |
127 | * as a substring of \a *this, beginning at character \a pos | |
128 | * of \a *this. If not found, returns size(). */ | |
129 | size_t find(const char* s, size_t pos=0) const; | |
130 | ||
131 | /** Searches backward for the character \a c, | |
132 | * beginning at character position \a min(pos, size()). */ | |
133 | size_t rfind(char c, size_t pos=max_string_len) const; | |
134 | ||
135 | /** Searches backward for a null-terminated character array | |
136 | * as a substring of \a *this, beginning at character | |
137 | * min(pos, size()) | |
138 | size_t rfind(const char* s, size_t pos=max_string_len) const; */ | |
139 | ||
140 | /** | |
141 | * Returns the first position \a i in the range [first, last) | |
142 | * such that <tt>pred((*this)[i]) != 0</tt>. | |
143 | * Returns \a last if no such position exists. | |
144 | * | |
145 | * I want to use this function like this: | |
146 | * \code size_t pos=str.find_if(0, str.size(), islower); \endcode | |
147 | */ | |
148 | size_t find_if(size_t first, size_t last, | |
149 | int (*pred)(int)) const; | |
150 | ||
151 | /** Returns whether \a c is a whitespace character */ | |
152 | static bool is_whitespace(unsigned char c); | |
153 | /** Returns whether \a c is a printable character */ | |
154 | static bool is_printable(unsigned char c); | |
155 | /** Appends the (possibly escaped) printable representation of character | |
156 | * \a c to \a this. Applicable only if \a c is a printable character. */ | |
157 | void append_stringRepr(char c); | |
158 | /** Returns the printable representation of charstring value stored in | |
159 | * \a this. The non-printable and special characters are escaped in the | |
160 | * returned string. */ | |
161 | string get_stringRepr() const; | |
162 | ||
163 | /** Creates universal string from pattern form: ([A-P]{8})* | |
164 | * | |
165 | */ | |
166 | ustring convert_stringRepr_for_pattern() const; | |
167 | ||
168 | /** Assignment operator. */ | |
169 | string& operator=(const string&); | |
170 | ||
171 | /** Assign a null-terminated character array to a string. */ | |
172 | string& operator=(const char *s); | |
173 | ||
174 | /** Returns the <em>n</em>th character. | |
175 | * The first character's position is zero. | |
176 | * If \a n >= size() then... Fatal error. */ | |
177 | char& operator[](size_t n); | |
178 | ||
179 | /** Returns the <em>n</em>th character. | |
180 | * The first character's position is zero. | |
181 | * If \a n >= size() then... Fatal error. */ | |
182 | char operator[](size_t n) const; | |
183 | ||
184 | /** String concatenation. */ | |
185 | string operator+(const string& s) const; | |
186 | ||
187 | /** String concatenation. */ | |
188 | string operator+(const char *s) const; | |
189 | ||
190 | /** Append \a s to \a *this. */ | |
191 | string& operator+=(const string& s); | |
192 | ||
193 | /** Append \a s to \a *this. */ | |
194 | string& operator+=(const char *s); | |
195 | ||
196 | /** Append \a c to \a *this. */ | |
197 | string& operator+=(char c) { copy_value_and_append(&c, 1); return *this; } | |
198 | ||
199 | /** String equality. Equivalent to this->compare(string(s)) == 0. */ | |
200 | bool operator==(const char *s) const; | |
201 | ||
202 | /** String equality. Equivalent to this->compare(s2) == 0. */ | |
203 | bool operator==(const string& s) const; | |
204 | ||
205 | /** String inequality. Equivalent to this->compare(s2) != 0. */ | |
206 | inline bool operator!=(const string& s) const { return !(*this == s); } | |
207 | ||
208 | /** String inequality. Equivalent to this->compare(string(s2)) != 0. */ | |
209 | inline bool operator!=(const char *s) const { return !(*this == s); } | |
210 | ||
211 | /** String comparison. */ | |
212 | inline bool operator<=(const string& s) const { return compare(s) <= 0; } | |
213 | ||
214 | /** String comparison. */ | |
215 | inline bool operator<=(const char *s) const { return compare(s) <= 0; } | |
216 | ||
217 | /** String comparison. */ | |
218 | inline bool operator<(const string& s) const { return compare(s) < 0; } | |
219 | ||
220 | /** String comparison. */ | |
221 | inline bool operator<(const char *s) const { return compare(s) < 0; } | |
222 | ||
223 | /** String comparison. */ | |
224 | inline bool operator>=(const string& s) const { return compare(s) >= 0; } | |
225 | ||
226 | /** String comparison. */ | |
227 | inline bool operator>=(const char *s) const { return compare(s) >= 0; } | |
228 | ||
229 | /** String comparison. */ | |
230 | inline bool operator>(const string& s) const { return compare(s) > 0; } | |
231 | ||
232 | /** String comparison. */ | |
233 | inline bool operator>(const char *s) const { return compare(s) > 0; } | |
234 | }; | |
235 | ||
236 | /** String concatenation. */ | |
237 | extern string operator+(const char *s1, const string& s2); | |
238 | ||
239 | /** String equality. */ | |
240 | inline bool operator==(const char *s1, const string& s2) { return s2 == s1; } | |
241 | ||
242 | /** String inequality. */ | |
243 | inline bool operator!=(const char *s1, const string& s2) { return !(s2 == s1); } | |
244 | ||
245 | /** | |
246 | * Class for preserving the memory allocated for temporary strings within a | |
247 | * statement block. | |
248 | */ | |
249 | class stringpool { | |
250 | string::string_struct **string_list; | |
251 | size_t list_size; /**< The number of strings allocated */ | |
252 | size_t list_len; /**< The number of strings in use. At most \a list_size */ | |
253 | /** Copy constructor not implemented */ | |
254 | stringpool(const stringpool& p); | |
255 | /** Assignment not implemented */ | |
256 | stringpool& operator=(const stringpool& p); | |
257 | ||
258 | public: | |
259 | /** Drops all strings from the pool. */ | |
260 | void clear(); | |
261 | /** Default constructor: creates an empty pool */ | |
262 | stringpool() : string_list(NULL), list_size(0), list_len(0) { } | |
263 | /** Destructor: drops the contents of the entire pool */ | |
264 | ~stringpool() { clear(); } | |
265 | /** Adds the current value of string \a s to the pool and returns its | |
266 | * pointer. The pointer is usable until \a this stringpool is destructed. */ | |
267 | const char *add(const string& s); | |
268 | /** Returns the number of strings in the pool */ | |
269 | size_t size() const { return list_len; } | |
270 | /** Returns the pointer to the \a n-th string of the pool */ | |
271 | const char *get_str(size_t n) const; | |
272 | /** Returns a newly constructed string containing the \a n-th element */ | |
273 | string get_string(size_t n) const; | |
274 | }; | |
275 | ||
276 | #endif // _Common_string_HH |