Skylicht Engine
Loading...
Searching...
No Matches
irrString.h
1// Copyright (C) 2002-2012 Nikolaus Gebhardt
2// This file is part of the "Irrlicht Engine" and the "irrXML" project.
3// For conditions of distribution and use, see copyright notice in irrlicht.h and irrXML.h
4
5#ifndef __IRR_STRING_H_INCLUDED__
6#define __IRR_STRING_H_INCLUDED__
7
8#include "irrTypes.h"
9#include "irrAllocator.h"
10#include "irrMath.h"
11#include <stdio.h>
12#include <string.h>
13#include <stdlib.h>
14
15namespace irr
16{
17namespace core
18{
19
21
34
36{
37 IRR_LOCALE_ANSI = 0,
38 IRR_LOCALE_GERMAN = 1
39};
40
41static eLocaleID locale_current = IRR_LOCALE_ANSI;
42static inline void locale_set ( eLocaleID id )
43{
44 locale_current = id;
45}
46
48static inline u32 locale_lower ( u32 x )
49{
50 switch ( locale_current )
51 {
52 case IRR_LOCALE_GERMAN:
53 case IRR_LOCALE_ANSI:
54 break;
55 }
56 // ansi
57 return x >= 'A' && x <= 'Z' ? x + 0x20 : x;
58}
59
61static inline u32 locale_upper ( u32 x )
62{
63 switch ( locale_current )
64 {
65 case IRR_LOCALE_GERMAN:
66 case IRR_LOCALE_ANSI:
67 break;
68 }
69
70 // ansi
71 return x >= 'a' && x <= 'z' ? x + ( 'A' - 'a' ) : x;
72}
73
75
78IRRLICHT_API void utf8ToWchar(const char *in, wchar_t *out, const u64 len);
79
81
84IRRLICHT_API void wcharToUtf8(const wchar_t *in, char *out, const u64 len);
85
86
87template <typename T, typename TAlloc = irrAllocator<T> >
88class string
89{
90public:
91
92 typedef T char_type;
93
96 : array(0), allocated(1), used(1)
97 {
98 array = allocator.allocate(1); // new T[1];
99 array[0] = 0;
100 }
101
102
105 : array(0), allocated(0), used(0)
106 {
107 *this = other;
108 }
109
111 template <class B, class A>
112 string(const string<B, A>& other)
113 : array(0), allocated(0), used(0)
114 {
115 *this = other;
116 }
117
118
120 explicit string(const double number)
121 : array(0), allocated(0), used(0)
122 {
123 c8 tmpbuf[255];
124 snprintf(tmpbuf, 255, "%0.6f", number);
125 *this = tmpbuf;
126 }
127
128
130 explicit string(int number)
131 : array(0), allocated(0), used(0)
132 {
133 // store if negative and make positive
134
135 bool negative = false;
136 if (number < 0)
137 {
138 number *= -1;
139 negative = true;
140 }
141
142 // temporary buffer for 16 numbers
143
144 c8 tmpbuf[16]={0};
145 u32 idx = 15;
146
147 // special case '0'
148
149 if (!number)
150 {
151 tmpbuf[14] = '0';
152 *this = &tmpbuf[14];
153 return;
154 }
155
156 // add numbers
157
158 while(number && idx)
159 {
160 --idx;
161 tmpbuf[idx] = (c8)('0' + (number % 10));
162 number /= 10;
163 }
164
165 // add sign
166
167 if (negative)
168 {
169 --idx;
170 tmpbuf[idx] = '-';
171 }
172
173 *this = &tmpbuf[idx];
174 }
175
176
178 explicit string(unsigned int number)
179 : array(0), allocated(0), used(0)
180 {
181 // temporary buffer for 16 numbers
182
183 c8 tmpbuf[16]={0};
184 u32 idx = 15;
185
186 // special case '0'
187
188 if (!number)
189 {
190 tmpbuf[14] = '0';
191 *this = &tmpbuf[14];
192 return;
193 }
194
195 // add numbers
196
197 while(number && idx)
198 {
199 --idx;
200 tmpbuf[idx] = (c8)('0' + (number % 10));
201 number /= 10;
202 }
203
204 *this = &tmpbuf[idx];
205 }
206
207
209 explicit string(long number)
210 : array(0), allocated(0), used(0)
211 {
212 // store if negative and make positive
213
214 bool negative = false;
215 if (number < 0)
216 {
217 number *= -1;
218 negative = true;
219 }
220
221 // temporary buffer for 16 numbers
222
223 c8 tmpbuf[16]={0};
224 u32 idx = 15;
225
226 // special case '0'
227
228 if (!number)
229 {
230 tmpbuf[14] = '0';
231 *this = &tmpbuf[14];
232 return;
233 }
234
235 // add numbers
236
237 while(number && idx)
238 {
239 --idx;
240 tmpbuf[idx] = (c8)('0' + (number % 10));
241 number /= 10;
242 }
243
244 // add sign
245
246 if (negative)
247 {
248 --idx;
249 tmpbuf[idx] = '-';
250 }
251
252 *this = &tmpbuf[idx];
253 }
254
255
257 explicit string(unsigned long number)
258 : array(0), allocated(0), used(0)
259 {
260 // temporary buffer for 16 numbers
261
262 c8 tmpbuf[16]={0};
263 u32 idx = 15;
264
265 // special case '0'
266
267 if (!number)
268 {
269 tmpbuf[14] = '0';
270 *this = &tmpbuf[14];
271 return;
272 }
273
274 // add numbers
275
276 while(number && idx)
277 {
278 --idx;
279 tmpbuf[idx] = (c8)('0' + (number % 10));
280 number /= 10;
281 }
282
283 *this = &tmpbuf[idx];
284 }
285
286
288 template <class B>
289 string(const B* const c, u32 length)
290 : array(0), allocated(0), used(0)
291 {
292 if (!c)
293 {
294 // correctly init the string to an empty one
295 *this="";
296 return;
297 }
298
299 allocated = used = length+1;
300 array = allocator.allocate(used); // new T[used];
301
302 for (u32 l = 0; l<length; ++l)
303 array[l] = (T)c[l];
304
305 array[length] = 0;
306 }
307
308
310 template <class B>
311 string(const B* const c)
312 : array(0), allocated(0), used(0)
313 {
314 *this = c;
315 }
316
317
320 {
321 allocator.deallocate(array); // delete [] array;
322 }
323
324
327 {
328 if (this == &other)
329 return *this;
330
331 used = other.size()+1;
332 if (used>allocated)
333 {
334 allocator.deallocate(array); // delete [] array;
335 allocated = used;
336 array = allocator.allocate(used); //new T[used];
337 }
338
339 const T* p = other.c_str();
340 for (u32 i=0; i<used; ++i, ++p)
341 array[i] = *p;
342
343 return *this;
344 }
345
347 template <class B, class A>
349 {
350 *this = other.c_str();
351 return *this;
352 }
353
354
356 template <class B>
357 string<T,TAlloc>& operator=(const B* const c)
358 {
359 if (!c)
360 {
361 if (!array)
362 {
363 array = allocator.allocate(1); //new T[1];
364 allocated = 1;
365 }
366 used = 1;
367 array[0] = 0x0;
368 return *this;
369 }
370
371 if ((void*)c == (void*)array)
372 return *this;
373
374 u32 len = 0;
375 const B* p = c;
376 do
377 {
378 ++len;
379 } while(*p++);
380
381 // we'll keep the old string for a while, because the new
382 // string could be a part of the current string.
383 T* oldArray = array;
384
385 used = len;
386 if (used>allocated)
387 {
388 allocated = used;
389 array = allocator.allocate(used); //new T[used];
390 }
391
392 for (u32 l = 0; l<len; ++l)
393 array[l] = (T)c[l];
394
395 if (oldArray != array)
396 allocator.deallocate(oldArray); // delete [] oldArray;
397
398 return *this;
399 }
400
401
404 {
405 string<T,TAlloc> str(*this);
406 str.append(other);
407
408 return str;
409 }
410
411
413 template <class B>
414 string<T,TAlloc> operator+(const B* const c) const
415 {
416 string<T,TAlloc> str(*this);
417 str.append(c);
418
419 return str;
420 }
421
422
424 T& operator [](const u32 index)
425 {
426 _IRR_DEBUG_BREAK_IF(index>=used) // bad index
427 return array[index];
428 }
429
430
432 const T& operator [](const u32 index) const
433 {
434 _IRR_DEBUG_BREAK_IF(index>=used) // bad index
435 return array[index];
436 }
437
438
440 bool operator==(const T* const str) const
441 {
442 if (!str)
443 return false;
444
445 u32 i;
446 for (i=0; array[i] && str[i]; ++i)
447 if (array[i] != str[i])
448 return false;
449
450 return (!array[i] && !str[i]);
451 }
452
453
455 bool operator==(const string<T,TAlloc>& other) const
456 {
457 for (u32 i=0; array[i] && other.array[i]; ++i)
458 if (array[i] != other.array[i])
459 return false;
460
461 return used == other.used;
462 }
463
464
466 bool operator<(const string<T,TAlloc>& other) const
467 {
468 for (u32 i=0; array[i] && other.array[i]; ++i)
469 {
470 const s32 diff = array[i] - other.array[i];
471 if (diff)
472 return (diff < 0);
473 }
474
475 return (used < other.used);
476 }
477
478
480 bool operator!=(const T* const str) const
481 {
482 return !(*this == str);
483 }
484
485
487 bool operator!=(const string<T,TAlloc>& other) const
488 {
489 return !(*this == other);
490 }
491
492
494
496 u32 size() const
497 {
498 return used-1;
499 }
500
503 bool empty() const
504 {
505 return (size() == 0);
506 }
507
509
510 const T* c_str() const
511 {
512 return array;
513 }
514
515
518 {
519 for (u32 i=0; array[i]; ++i)
520 array[i] = locale_lower ( array[i] );
521 return *this;
522 }
523
524
527 {
528 for (u32 i=0; array[i]; ++i)
529 array[i] = locale_upper ( array[i] );
530 return *this;
531 }
532
533
535
537 bool equals_ignore_case(const string<T,TAlloc>& other) const
538 {
539 for(u32 i=0; array[i] && other[i]; ++i)
540 if (locale_lower( array[i]) != locale_lower(other[i]))
541 return false;
542
543 return used == other.used;
544 }
545
547
550 bool equals_substring_ignore_case(const string<T,TAlloc>&other, const s32 sourcePos = 0 ) const
551 {
552 if ( (u32) sourcePos >= used )
553 return false;
554
555 u32 i;
556 for( i=0; array[sourcePos + i] && other[i]; ++i)
557 if (locale_lower( array[sourcePos + i]) != locale_lower(other[i]))
558 return false;
559
560 return array[sourcePos + i] == 0 && other[i] == 0;
561 }
562
563
565
567 bool lower_ignore_case(const string<T,TAlloc>& other) const
568 {
569 for(u32 i=0; array[i] && other.array[i]; ++i)
570 {
571 s32 diff = (s32) locale_lower ( array[i] ) - (s32) locale_lower ( other.array[i] );
572 if ( diff )
573 return diff < 0;
574 }
575
576 return used < other.used;
577 }
578
579
581
584 bool equalsn(const string<T,TAlloc>& other, u32 n) const
585 {
586 u32 i;
587 for(i=0; i < n && array[i] && other[i]; ++i)
588 if (array[i] != other[i])
589 return false;
590
591 // if one (or both) of the strings was smaller then they
592 // are only equal if they have the same length
593 return (i == n) || (used == other.used);
594 }
595
596
598
601 bool equalsn(const T* const str, u32 n) const
602 {
603 if (!str)
604 return false;
605 u32 i;
606 for(i=0; i < n && array[i] && str[i]; ++i)
607 if (array[i] != str[i])
608 return false;
609
610 // if one (or both) of the strings was smaller then they
611 // are only equal if they have the same length
612 return (i == n) || (array[i] == 0 && str[i] == 0);
613 }
614
615
617
619 {
620 if (used + 1 > allocated)
621 reallocate(used + 1);
622
623 ++used;
624
625 array[used-2] = character;
626 array[used-1] = 0;
627
628 return *this;
629 }
630
631
633
635 string<T,TAlloc>& append(const T* const other, u32 length=0xffffffff)
636 {
637 if (!other)
638 return *this;
639
640 u32 len = 0;
641 const T* p = other;
642 while(*p)
643 {
644 ++len;
645 ++p;
646 }
647 if (len > length)
648 len = length;
649
650 if (used + len > allocated)
651 reallocate(used + len);
652
653 --used;
654 ++len;
655
656 for (u32 l=0; l<len; ++l)
657 array[l+used] = *(other+l);
658
659 used += len;
660
661 return *this;
662 }
663
664
666
668 {
669 if (other.size() == 0)
670 return *this;
671
672 --used;
673 u32 len = other.size()+1;
674
675 if (used + len > allocated)
676 reallocate(used + len);
677
678 for (u32 l=0; l<len; ++l)
679 array[used+l] = other[l];
680
681 used += len;
682
683 return *this;
684 }
685
686
688
691 {
692 if (other.size() == 0)
693 return *this;
694
695 if (other.size() < length)
696 {
697 append(other);
698 return *this;
699 }
700
701 if (used + length > allocated)
702 reallocate(used + length);
703
704 --used;
705
706 for (u32 l=0; l<length; ++l)
707 array[l+used] = other[l];
708 used += length;
709
710 // ensure proper termination
711 array[used]=0;
712 ++used;
713
714 return *this;
715 }
716
717
719
720 void reserve(u32 count)
721 {
722 if (count < allocated)
723 return;
724
725 reallocate(count);
726 }
727
728
730
733 s32 findFirst(T c) const
734 {
735 for (u32 i=0; i<used-1; ++i)
736 if (array[i] == c)
737 return i;
738
739 return -1;
740 }
741
743
749 s32 findFirstChar(const T* const c, u32 count=1) const
750 {
751 if (!c || !count)
752 return -1;
753
754 for (u32 i=0; i<used-1; ++i)
755 for (u32 j=0; j<count; ++j)
756 if (array[i] == c[j])
757 return i;
758
759 return -1;
760 }
761
762
764
770 template <class B>
771 s32 findFirstCharNotInList(const B* const c, u32 count=1) const
772 {
773 if (!c || !count)
774 return -1;
775
776 for (u32 i=0; i<used-1; ++i)
777 {
778 u32 j;
779 for (j=0; j<count; ++j)
780 if (array[i] == c[j])
781 break;
782
783 if (j==count)
784 return i;
785 }
786
787 return -1;
788 }
789
791
797 template <class B>
798 s32 findLastCharNotInList(const B* const c, u32 count=1) const
799 {
800 if (!c || !count)
801 return -1;
802
803 for (s32 i=(s32)(used-2); i>=0; --i)
804 {
805 u32 j;
806 for (j=0; j<count; ++j)
807 if (array[i] == c[j])
808 break;
809
810 if (j==count)
811 return i;
812 }
813
814 return -1;
815 }
816
818
822 s32 findNext(T c, u32 startPos) const
823 {
824 for (u32 i=startPos; i<used-1; ++i)
825 if (array[i] == c)
826 return i;
827
828 return -1;
829 }
830
831
833
837 s32 findLast(T c, s32 start = -1) const
838 {
839 start = core::clamp ( start < 0 ? (s32)(used) - 2 : start, 0, (s32)(used) - 2 );
840 for (s32 i=start; i>=0; --i)
841 if (array[i] == c)
842 return i;
843
844 return -1;
845 }
846
848
854 s32 findLastChar(const T* const c, u32 count=1) const
855 {
856 if (!c || !count)
857 return -1;
858
859 for (s32 i=(s32)used-2; i>=0; --i)
860 for (u32 j=0; j<count; ++j)
861 if (array[i] == c[j])
862 return i;
863
864 return -1;
865 }
866
867
869
873 template <class B>
874 s32 find(const B* const str, const u32 start = 0) const
875 {
876 if (str && *str)
877 {
878 u32 len = 0;
879
880 while (str[len])
881 ++len;
882
883 if (len > used-1)
884 return -1;
885
886 for (u32 i=start; i<used-len; ++i)
887 {
888 u32 j=0;
889
890 while(str[j] && array[i+j] == str[j])
891 ++j;
892
893 if (!str[j])
894 return i;
895 }
896 }
897
898 return -1;
899 }
900
901
903
906 string<T> subString(u32 begin, s32 length, bool make_lower = false ) const
907 {
908 // if start after string
909 // or no proper substring length
910 if ((length <= 0) || (begin>=size()))
911 return string<T>("");
912 // clamp length to maximal value
913 if ((length+begin) > size())
914 length = size()-begin;
915
916 string<T> o;
917 o.reserve(length+1);
918
919 s32 i;
920 if ( !make_lower )
921 {
922 for (i=0; i<length; ++i)
923 o.array[i] = array[i+begin];
924 }
925 else
926 {
927 for (i=0; i<length; ++i)
928 o.array[i] = locale_lower ( array[i+begin] );
929 }
930
931 o.array[length] = 0;
932 o.used = length + 1;
933
934 return o;
935 }
936
937
939
941 {
942 append(c);
943 return *this;
944 }
945
946
948
950 {
951 append(c);
952 return *this;
953 }
954
955
957
959 {
960 append(other);
961 return *this;
962 }
963
964
966
968 {
970 return *this;
971 }
972
973
975
976 string<T,TAlloc>& operator += (const unsigned int i)
977 {
979 return *this;
980 }
981
982
984
986 {
988 return *this;
989 }
990
991
993
994 string<T,TAlloc>& operator += (const unsigned long i)
995 {
997 return *this;
998 }
999
1000
1002
1004 {
1006 return *this;
1007 }
1008
1009
1011
1013 {
1015 return *this;
1016 }
1017
1018
1020
1022 string<T,TAlloc>& replace(T toReplace, T replaceWith)
1023 {
1024 for (u32 i=0; i<used-1; ++i)
1025 if (array[i] == toReplace)
1026 array[i] = replaceWith;
1027 return *this;
1028 }
1029
1030
1032
1034 string<T,TAlloc>& replace(const string<T,TAlloc>& toReplace, const string<T,TAlloc>& replaceWith)
1035 {
1036 if (toReplace.size() == 0)
1037 return *this;
1038
1039 const T* other = toReplace.c_str();
1040 const T* replace = replaceWith.c_str();
1041 const u32 other_size = toReplace.size();
1042 const u32 replace_size = replaceWith.size();
1043
1044 // Determine the delta. The algorithm will change depending on the delta.
1045 s32 delta = replace_size - other_size;
1046
1047 // A character for character replace. The string will not shrink or grow.
1048 if (delta == 0)
1049 {
1050 s32 pos = 0;
1051 while ((pos = find(other, pos)) != -1)
1052 {
1053 for (u32 i = 0; i < replace_size; ++i)
1054 array[pos + i] = replace[i];
1055 ++pos;
1056 }
1057 return *this;
1058 }
1059
1060 // We are going to be removing some characters. The string will shrink.
1061 if (delta < 0)
1062 {
1063 u32 i = 0;
1064 for (u32 pos = 0; pos < used; ++i, ++pos)
1065 {
1066 // Is this potentially a match?
1067 if (array[pos] == *other)
1068 {
1069 // Check to see if we have a match.
1070 u32 j;
1071 for (j = 0; j < other_size; ++j)
1072 {
1073 if (array[pos + j] != other[j])
1074 break;
1075 }
1076
1077 // If we have a match, replace characters.
1078 if (j == other_size)
1079 {
1080 for (j = 0; j < replace_size; ++j)
1081 array[i + j] = replace[j];
1082 i += replace_size - 1;
1083 pos += other_size - 1;
1084 continue;
1085 }
1086 }
1087
1088 // No match found, just copy characters.
1089 array[i] = array[pos];
1090 }
1091 array[i-1] = 0;
1092 used = i;
1093
1094 return *this;
1095 }
1096
1097 // We are going to be adding characters, so the string size will increase.
1098 // Count the number of times toReplace exists in the string so we can allocate the new size.
1099 u32 find_count = 0;
1100 s32 pos = 0;
1101 while ((pos = find(other, pos)) != -1)
1102 {
1103 ++find_count;
1104 ++pos;
1105 }
1106
1107 // Re-allocate the string now, if needed.
1108 u32 len = delta * find_count;
1109 if (used + len > allocated)
1110 reallocate(used + len);
1111
1112 // Start replacing.
1113 pos = 0;
1114 while ((pos = find(other, pos)) != -1)
1115 {
1116 T* start = array + pos + other_size - 1;
1117 T* ptr = array + used - 1;
1118 T* end = array + delta + used -1;
1119
1120 // Shift characters to make room for the string.
1121 while (ptr != start)
1122 {
1123 *end = *ptr;
1124 --ptr;
1125 --end;
1126 }
1127
1128 // Add the new string now.
1129 for (u32 i = 0; i < replace_size; ++i)
1130 array[pos + i] = replace[i];
1131
1132 pos += replace_size;
1133 used += delta;
1134 }
1135
1136 return *this;
1137 }
1138
1139
1141
1143 {
1144 u32 pos = 0;
1145 u32 found = 0;
1146 for (u32 i=0; i<used-1; ++i)
1147 {
1148 if (array[i] == c)
1149 {
1150 ++found;
1151 continue;
1152 }
1153
1154 array[pos++] = array[i];
1155 }
1156 used -= found;
1157 array[used-1] = 0;
1158 return *this;
1159 }
1160
1161
1163
1165 {
1166 u32 size = toRemove.size();
1167 if ( size == 0 )
1168 return *this;
1169 u32 pos = 0;
1170 u32 found = 0;
1171 for (u32 i=0; i<used-1; ++i)
1172 {
1173 u32 j = 0;
1174 while (j < size)
1175 {
1176 if (array[i + j] != toRemove[j])
1177 break;
1178 ++j;
1179 }
1180 if (j == size)
1181 {
1182 found += size;
1183 i += size - 1;
1184 continue;
1185 }
1186
1187 array[pos++] = array[i];
1188 }
1189 used -= found;
1190 array[used-1] = 0;
1191 return *this;
1192 }
1193
1194
1196
1198 {
1199 if (characters.size() == 0)
1200 return *this;
1201
1202 u32 pos = 0;
1203 u32 found = 0;
1204 for (u32 i=0; i<used-1; ++i)
1205 {
1206 // Don't use characters.findFirst as it finds the \0,
1207 // causing used to become incorrect.
1208 bool docontinue = false;
1209 for (u32 j=0; j<characters.size(); ++j)
1210 {
1211 if (characters[j] == array[i])
1212 {
1213 ++found;
1214 docontinue = true;
1215 break;
1216 }
1217 }
1218 if (docontinue)
1219 continue;
1220
1221 array[pos++] = array[i];
1222 }
1223 used -= found;
1224 array[used-1] = 0;
1225
1226 return *this;
1227 }
1228
1229
1231
1233 string<T,TAlloc>& trim(const string<T,TAlloc> & whitespace = " \t\n\r")
1234 {
1235 // find start and end of the substring without the specified characters
1236 const s32 begin = findFirstCharNotInList(whitespace.c_str(), whitespace.used);
1237 if (begin == -1)
1238 return (*this="");
1239
1240 const s32 end = findLastCharNotInList(whitespace.c_str(), whitespace.used);
1241
1242 return (*this = subString(begin, (end +1) - begin));
1243 }
1244
1245
1247
1251 {
1252 _IRR_DEBUG_BREAK_IF(index>=used) // access violation
1253
1254 for (u32 i=index+1; i<used; ++i)
1255 array[i-1] = array[i];
1256
1257 --used;
1258 return *this;
1259 }
1260
1263 {
1264 // terminate on existing null
1265 for (u32 i=0; i<allocated; ++i)
1266 {
1267 if (array[i] == 0)
1268 {
1269 used = i + 1;
1270 return *this;
1271 }
1272 }
1273
1274 // terminate
1275 if ( allocated > 0 )
1276 {
1277 used = allocated;
1278 array[used-1] = 0;
1279 }
1280 else
1281 {
1282 used = 0;
1283 }
1284
1285 return *this;
1286 }
1287
1289 T lastChar() const
1290 {
1291 return used > 1 ? array[used-2] : 0;
1292 }
1293
1295
1312 template<class container>
1313 u32 split(container& ret, const T* const c, u32 count=1, bool ignoreEmptyTokens=true, bool keepSeparators=false) const
1314 {
1315 if (!c)
1316 return 0;
1317
1318 const u32 oldSize=ret.size();
1319 u32 lastpos = 0;
1320 bool lastWasSeparator = false;
1321 for (u32 i=0; i<used; ++i)
1322 {
1323 bool foundSeparator = false;
1324 for (u32 j=0; j<count; ++j)
1325 {
1326 if (array[i] == c[j])
1327 {
1328 if ((!ignoreEmptyTokens || i - lastpos != 0) &&
1329 !lastWasSeparator)
1330 ret.push_back(string<T,TAlloc>(&array[lastpos], i - lastpos));
1331 foundSeparator = true;
1332 lastpos = (keepSeparators ? i : i + 1);
1333 break;
1334 }
1335 }
1336 lastWasSeparator = foundSeparator;
1337 }
1338 if ((used - 1) > lastpos)
1339 ret.push_back(string<T,TAlloc>(&array[lastpos], (used - 1) - lastpos));
1340 return ret.size()-oldSize;
1341 }
1342
1343private:
1344
1346 void reallocate(u32 new_size)
1347 {
1348 T* old_array = array;
1349
1350 array = allocator.allocate(new_size); //new T[new_size];
1351 allocated = new_size;
1352
1353 u32 amount = used < new_size ? used : new_size;
1354 for (u32 i=0; i<amount; ++i)
1355 array[i] = old_array[i];
1356
1357 if (allocated < used)
1358 used = allocated;
1359
1360 allocator.deallocate(old_array); // delete [] old_array;
1361 }
1362
1363 //--- member variables
1364
1365 T* array;
1366 u32 allocated;
1367 u32 used;
1368 TAlloc allocator;
1369};
1370
1371
1374
1377
1378} // end namespace core
1379} // end namespace irr
1380
1381#endif
1382
Self reallocating template array (like stl vector) with additional features.
Definition irrArray.h:23
Definition irrString.h:89
~string()
Destructor.
Definition irrString.h:319
string< T, TAlloc > & append(const T *const other, u32 length=0xffffffff)
Appends a char string to this string.
Definition irrString.h:635
s32 findFirstChar(const T *const c, u32 count=1) const
finds first occurrence of a character of a list in string
Definition irrString.h:749
u32 size() const
Returns length of the string's content.
Definition irrString.h:496
bool equals_ignore_case(const string< T, TAlloc > &other) const
Compares the strings ignoring case.
Definition irrString.h:537
s32 find(const B *const str, const u32 start=0) const
finds another string in this string
Definition irrString.h:874
bool operator!=(const T *const str) const
Inequality operator.
Definition irrString.h:480
string< T, TAlloc > & operator+=(T c)
Appends a character to this string.
Definition irrString.h:940
string(long number)
Constructs a string from a long.
Definition irrString.h:209
s32 findFirst(T c) const
finds first occurrence of character in string
Definition irrString.h:733
string(unsigned long number)
Constructs a string from an unsigned long.
Definition irrString.h:257
s32 findFirstCharNotInList(const B *const c, u32 count=1) const
Finds first position of a character not in a given list.
Definition irrString.h:771
bool operator==(const string< T, TAlloc > &other) const
Equality operator.
Definition irrString.h:455
string< T, TAlloc > & validate()
verify the existing string.
Definition irrString.h:1262
string(int number)
Constructs a string from an int.
Definition irrString.h:130
string< T, TAlloc > & append(T character)
Appends a character to this string.
Definition irrString.h:618
void reserve(u32 count)
Reserves some memory.
Definition irrString.h:720
string< T, TAlloc > & trim(const string< T, TAlloc > &whitespace=" \t\n\r")
Trims the string.
Definition irrString.h:1233
string< T, TAlloc > & remove(const string< T, TAlloc > &toRemove)
Removes a string from the string.
Definition irrString.h:1164
string< T > subString(u32 begin, s32 length, bool make_lower=false) const
Returns a substring.
Definition irrString.h:906
s32 findLast(T c, s32 start=-1) const
finds last occurrence of character in string
Definition irrString.h:837
string< T, TAlloc > & append(const string< T, TAlloc > &other)
Appends a string to this string.
Definition irrString.h:667
string< T, TAlloc > & operator=(const B *const c)
Assignment operator for strings, ascii and unicode.
Definition irrString.h:357
string(const B *const c)
Constructor for unicode and ascii strings.
Definition irrString.h:311
string()
Default constructor.
Definition irrString.h:95
T lastChar() const
gets the last char of a string or null
Definition irrString.h:1289
string< T, TAlloc > & operator=(const string< B, A > &other)
Assignment operator for other string types.
Definition irrString.h:348
bool operator<(const string< T, TAlloc > &other) const
Is smaller comparator.
Definition irrString.h:466
string(const B *const c, u32 length)
Constructor for copying a string from a pointer with a given length.
Definition irrString.h:289
string< T, TAlloc > & replace(T toReplace, T replaceWith)
Replaces all characters of a special type with another one.
Definition irrString.h:1022
s32 findLastChar(const T *const c, u32 count=1) const
finds last occurrence of a character of a list in string
Definition irrString.h:854
string(const string< B, A > &other)
Constructor from other string types.
Definition irrString.h:112
string(unsigned int number)
Constructs a string from an unsigned int.
Definition irrString.h:178
s32 findNext(T c, u32 startPos) const
finds next occurrence of character in string
Definition irrString.h:822
string< T, TAlloc > & replace(const string< T, TAlloc > &toReplace, const string< T, TAlloc > &replaceWith)
Replaces all instances of a string with another one.
Definition irrString.h:1034
string< T, TAlloc > & operator=(const string< T, TAlloc > &other)
Assignment operator.
Definition irrString.h:326
string< T, TAlloc > & erase(u32 index)
Erases a character from the string.
Definition irrString.h:1250
string< T, TAlloc > & make_upper()
Makes the string upper case.
Definition irrString.h:526
s32 findLastCharNotInList(const B *const c, u32 count=1) const
Finds last position of a character not in a given list.
Definition irrString.h:798
bool lower_ignore_case(const string< T, TAlloc > &other) const
Compares the strings ignoring case.
Definition irrString.h:567
string< T, TAlloc > operator+(const string< T, TAlloc > &other) const
Append operator for other strings.
Definition irrString.h:403
string(const double number)
Constructs a string from a float.
Definition irrString.h:120
string(const string< T, TAlloc > &other)
Constructor.
Definition irrString.h:104
u32 split(container &ret, const T *const c, u32 count=1, bool ignoreEmptyTokens=true, bool keepSeparators=false) const
split string into parts.
Definition irrString.h:1313
bool operator!=(const string< T, TAlloc > &other) const
Inequality operator.
Definition irrString.h:487
string< T, TAlloc > & append(const string< T, TAlloc > &other, u32 length)
Appends a string of the length l to this string.
Definition irrString.h:690
const T * c_str() const
Returns character string.
Definition irrString.h:510
string< T, TAlloc > & removeChars(const string< T, TAlloc > &characters)
Removes characters from a string.
Definition irrString.h:1197
string< T, TAlloc > & make_lower()
Makes the string lower case.
Definition irrString.h:517
string< T, TAlloc > & remove(T c)
Removes characters from a string.
Definition irrString.h:1142
bool equalsn(const T *const str, u32 n) const
compares the first n characters of the strings
Definition irrString.h:601
bool equals_substring_ignore_case(const string< T, TAlloc > &other, const s32 sourcePos=0) const
Compares the strings ignoring case.
Definition irrString.h:550
bool equalsn(const string< T, TAlloc > &other, u32 n) const
compares the first n characters of the strings
Definition irrString.h:584
bool operator==(const T *const str) const
Equality operator.
Definition irrString.h:440
string< T, TAlloc > operator+(const B *const c) const
Append operator for strings, ascii and unicode.
Definition irrString.h:414
T & operator[](const u32 index)
Direct access operator.
Definition irrString.h:424
bool empty() const
Definition irrString.h:503
Basic classes such as vectors, planes, arrays, lists, and so on can be found in this namespace.
Definition aabbox3d.h:15
eLocaleID
Very simple string class with some useful features.
Definition irrString.h:36
IRRLICHT_API void wcharToUtf8(const wchar_t *in, char *out, const u64 len)
Convert this wchar string to utf-8.
const T clamp(const T &value, const T &low, const T &high)
clamps a value between low and high
Definition irrMath.h:166
string< c8 > stringc
Typedef for character strings.
Definition irrString.h:1373
IRRLICHT_API void utf8ToWchar(const char *in, wchar_t *out, const u64 len)
Convert this utf-8-encoded string to the platform's wchar.
string< wchar_t > stringw
Typedef for wide character strings.
Definition irrString.h:1376
Everything in the Irrlicht Engine can be found in this namespace.
Definition Skylicht.h:33
unsigned int u32
32 bit unsigned variable.
Definition irrTypes.h:58
char c8
8 bit character variable.
Definition irrTypes.h:31
unsigned long long u64
64 bit unsigned variable.
Definition irrTypes.h:82
signed int s32
32 bit signed variable.
Definition irrTypes.h:66