6#ifndef _ZFI_zfstring_h_
7#define _ZFI_zfstring_h_
19template<
int minCapacityRadix>
21 capacity >>= minCapacityRadix;
22 capacity |= capacity >> 1;
23 capacity |= capacity >> 2;
24 capacity |= capacity >> 4;
25 capacity |= capacity >> 8;
26 capacity |= capacity >> 16;
28 capacity <<= minCapacityRadix;
32template<
typename T_Char>
41template<
typename T_Char>
42zfint _ZFP_zfstring_cmp(
43 ZF_IN const T_Char *s1
44 ,
ZF_IN const T_Char *s1End
45 ,
ZF_IN const T_Char *s2
46 ,
ZF_IN const T_Char *s2End
48 while(s1 < s1End && s2 < s2End && *s1 == *s2) {++s1, ++s2;}
67template<
typename T_Char>
82 _ZFP_zfstringD(
void) : refCount(1), capacity(0), length(0), d() {
85 ~_ZFP_zfstringD(
void) {
86 if(this->capacity >= 2 ) {
91 static const T_Char *Empty(
void) {
92 static T_Char buf[1] = {0};
96template<
typename T_Char>
99 _ZFP_zfstringH(
void) : d(
zfpoolNew(_ZFP_zfstringD<T_Char>)) {}
102 _ZFP_zfstringD<T_Char> *d;
109template<
typename T_Char>
132 if(len >= s.length()) {
136 this->
assign(s.cString(), len);
145 if(pos < s.length()) {
146 if(len > s.length() - pos) {
147 len = s.length() - pos;
149 this->
assign(s.cString() + pos, len);
179 this->
assign(s + pos, len);
191 if(--(d->refCount) == 0) {
198 inline operator const T_Char * (void)
const {
199 return this->isEmpty() ?
zfnull : this->cString();
201 inline operator zfbool (
void)
const {
202 return !this->isEmpty();
208 _ZFP_zfstringD<T_Char> *dTmp = d;
211 if(--(dTmp->refCount) == 0) {
221 zfbool operator == (
ZF_IN const T_Char *ref)
const {
return this->isEqual(ref);}
222 zfbool operator != (
ZF_IN const T_Char *ref)
const {
return !this->isEqual(ref);}
239 template<
typename T_Int>
241 return this->cString() + offset;
253 _prepareWrite(this->length());
260 return d->d.ptr[pos];
264 template<
typename T_Int>
265 inline T_Char operator [] (
ZF_IN T_Int pos)
const {
266 return this->get(pos);
277 _ZFP_zfstringD<T_Char> *dTmp = d;
285 _prepareWrite(d->length + 1);
286 d->d.buf[d->length] = c;
287 d->d.buf[++(d->length)] =
'\0';
293 if(this->capacity() != 0) {
294 _appendImpl(s.cString(), s.length());
297 this->operator = (s);
307 len = (len <= s.length() ? len : s.length());
309 _appendImpl(s.cString(), len);
319 if(offset > s.length()) {
322 if(len > s.length() - offset) {
323 len = s.length() - offset;
326 _appendImpl(s.cString() + offset, len);
337 len = _ZFP_zfstring_len((
const T_Char *)s);
350 _prepareWrite(d->length + len);
351 zfmemcpy(d->d.buf + d->length, s, len *
sizeof(T_Char));
352 d->d.buf[d->length += (
zfuint)len] =
'\0';
358 this->operator = (s);
366 return this->
assign(s.cString(), len <= s.length() ? len : s.length());
374 if(offset > s.length()) {
377 if(len > s.length() - offset) {
378 len = s.length() - offset;
380 return this->
assign(s.cString() + offset, len);
389 len = _ZFP_zfstring_len((
const T_Char *)s);
396 if(len >= d->capacity || d->refCount > 1
397 || (d->capacity >= 128 && len < d->
capacity / 3)
402 zfmemcpy(d->d.buf, s, len *
sizeof(T_Char));
403 d->d.buf[len] =
'\0';
422 return this->
insert(insertAt, s.cString(), s.length());
427 ,
ZF_IN const void *s
430 if(insertAt >= this->length()) {
435 len = _ZFP_zfstring_len((
const T_Char *)s);
438 zfindex lenTmp = this->length();
439 _prepareWrite(lenTmp + len);
440 d->length = (
zfuint)(lenTmp + len);
441 zfmemmove(d->d.buf + insertAt + len, d->d.buf + insertAt, (lenTmp - insertAt) *
sizeof(T_Char));
442 zfmemcpy(d->d.buf + insertAt, s, len *
sizeof(T_Char));
443 d->d.buf[d->length] =
'\0';
456 return this->
replace(replacePos, replaceLen, s.cString(), s.length());
462 ,
ZF_IN const void *s
465 if(replacePos >= this->length()) {
469 zfindex lenTmp = this->length();
470 if(replaceLen > lenTmp - replacePos) {
471 replaceLen = lenTmp - replacePos;
474 len = _ZFP_zfstring_len((
const T_Char *)s);
476 if(len > replaceLen) {
477 _prepareWrite(lenTmp + len - replaceLen);
480 _prepareWrite(lenTmp);
482 zfmemmove(d->d.buf + replacePos + len, d->d.buf + replacePos + replaceLen, (lenTmp - replacePos - replaceLen) *
sizeof(T_Char));
483 zfmemcpy(d->d.buf + replacePos, s, len *
sizeof(T_Char));
484 d->length = (
zfuint)(lenTmp + len - replaceLen);
485 d->d.buf[d->length] =
'\0';
503 return d->capacity < _ZFP_ST_Normal && d->length > 0;
507 return d->length == 0;
511 return d == ref.d || (this->length() == ref.length() && this->
compare(ref) == 0);
515 return 0 == _ZFP_zfstring_cmp(this->
cString(), this->
cString() + this->length(), s, s + (s ? _ZFP_zfstring_len(s) : 0));
530 if(d->capacity >= _ZFP_ST_Normal) {
539 if(d->capacity >= 128 && d->length < d->capacity / 3) {
540 _capacityChange(this->length(),
zftrue);
548 zfindex lenTmp = this->length();
550 if(len > lenTmp - pos) {
554 _prepareWrite(lenTmp);
555 zfmemmove(d->d.buf + pos, d->d.buf + pos + len, (lenTmp - pos - len) *
sizeof(T_Char));
557 d->d.buf[d->length] =
'\0';
565 if(d->refCount == 1) {
566 if(d->capacity >= 128) {
567 if(--(d->refCount) == 0) {
573 else if(d->capacity >= _ZFP_ST_Normal) {
578 d->d.ptr = _ZFP_zfstringD<T_Char>::Empty();
583 if(--(d->refCount) == 0) {
595 return d == s.d ? 0 : _ZFP_zfstring_cmp(this->
cString(), this->
cString() + this->length(), s.cString(), s.cString() + s.length());
599 ZF_IN const T_Char *s
603 len = s ? _ZFP_zfstring_len(s) : 0;
605 return _ZFP_zfstring_cmp(this->
cString(), this->
cString() + this->length(), s, s + (s ? _ZFP_zfstring_len(s) : 0));
622 _prepareWrite(this->length());
623 ret = (
void *)d->d.buf;
628 d->d.ptr = _ZFP_zfstringD<T_Char>::Empty();
645 _prepareWrite(this->length());
652 _prepareWrite(this->length());
662 _ZFP_zfstringD<T_Char> *d;
685 ZF_IN const void *sLiteral
690 d->d.ptr = (
const T_Char *)sLiteral;
692 d->capacity = _ZFP_ST_Shared;
699 const T_Char *ptr = d->d.ptr;
707 d->d.buf[d->length] =
'\0';
717 static _ZFP_zfstringD<T_Char> *_ZFP_Empty(
void) {
718 static _ZFP_zfstringH<T_Char> d;
726 _capacityOptimize(capacity);
728 if(d->refCount == 1) {
729 if(d->capacity >= _ZFP_ST_Normal) {
737 const T_Char *ptr = d->d.ptr;
743 if(ptr && keepContents) {
744 zfmemcpy(d->d.buf, ptr, capacity *
sizeof(T_Char));
756 _ZFP_zfstringD<T_Char> *dTmp = d;
758 d->length = dTmp->length;
760 if(dTmp->length > 0 && keepContents) {
761 zfmemcpy(d->d.buf, dTmp->d.ptr, dTmp->length *
sizeof(T_Char));
762 d->d.buf[dTmp->length] =
'\0';
768 d->capacity = (
zfuint)capacity;
775 if(len >= d->capacity || d->refCount > 1) {
776 _capacityChange(len,
zftrue);
785 #define zftext(s, ...) zfstring::shared(s, ##__VA_ARGS__)
#define ZFCoreMutexLocker()
util method to lock current block
Definition ZFCoreMutex.h:95
zfindex zfslen(const zfchar *s)
strlen wrapper as zfchar type
Definition ZFCoreTypeDef_CharType.h:144
_ZFT_t_zfchar zfchar
char wrapper
Definition ZFCoreTypeDef_CharType.h:17
#define zfclassLikePOD
shows the class is not a POD type, but you may use it like a POD except memset it to 0
Definition ZFCoreTypeDef_ClassType.h:41
#define ZF_IN
dummy macro that shows the param used as required input
Definition ZFCoreTypeDef_ClassType.h:196
#define ZF_IN_OPT
dummy macro that shows the param used as optional input
Definition ZFCoreTypeDef_ClassType.h:200
void * zfmemmove(void *dst, const void *src, zfindex size)
wrapper to memmove
Definition ZFCoreTypeDef_ClassType.h:158
#define ZF_OUT
dummy macro that shows the param used as required output
Definition ZFCoreTypeDef_ClassType.h:204
#define zfclassNotPOD
shows the class is not a POD type, you should not memset it or declare it in stack or copy value by c...
Definition ZFCoreTypeDef_ClassType.h:48
#define ZF_IN_OUT
dummy macro that shows the param used as required input and output
Definition ZFCoreTypeDef_ClassType.h:212
void * zfmemcpy(void *dst, const void *src, zfindex size)
wrapper to memcpy
Definition ZFCoreTypeDef_ClassType.h:156
#define zfnullT
type for zfnull, can be used for function overload
Definition ZFCoreTypeDef_CoreType.h:85
_ZFT_t_zfbool zfbool
bool type
Definition ZFCoreTypeDef_CoreType.h:103
_ZFT_t_zfindex zfindex
similar to size_t, used for index and size only
Definition ZFCoreTypeDef_CoreType.h:154
#define zftrue
bool true type
Definition ZFCoreTypeDef_CoreType.h:107
_ZFT_t_zfint zfint
same as int, see zfindex
Definition ZFCoreTypeDef_CoreType.h:165
#define zfindexMax()
(zfindex)-1, indicate a max index value, see zfindex
Definition ZFCoreTypeDef_CoreType.h:159
#define zffalse
bool false type
Definition ZFCoreTypeDef_CoreType.h:111
#define zfnull
same as NULL, defined for future use
Definition ZFCoreTypeDef_CoreType.h:88
_ZFT_t_zfuint zfuint
same as unsigned int, see zfindex
Definition ZFCoreTypeDef_CoreType.h:169
#define zfunsafe_zfpoolNew(T_Type,...)
see zfnew
Definition ZFMemPool.h:44
#define zfpoolDelete(obj)
see zfnew
Definition ZFMemPool.h:81
#define zfunsafe_zfpoolRealloc(p, size)
see zfnew
Definition ZFMemPool.h:63
#define zfunsafe_zfpoolDelete(obj)
see zfnew
Definition ZFMemPool.h:45
#define zfunsafe_zfpoolMalloc(size)
see zfnew
Definition ZFMemPool.h:62
#define zfunsafe_zfpoolFree(p)
see zfnew
Definition ZFMemPool.h:64
#define zfpoolFree(p)
see zfnew
Definition ZFMemPool.h:100
#define zfpoolNew(T_Type,...)
see zfnew
Definition ZFMemPool.h:80
#define ZF_NAMESPACE_GLOBAL_BEGIN
begin namespace ZFFramework
Definition ZFNamespace.h:97
#define ZF_NAMESPACE_GLOBAL_END
end namespace ZFFramework
Definition ZFNamespace.h:98
ZFUIMargin & operator+=(ZFUIMargin &v0, const ZFUIMargin &v1)
v0 += v1
Definition ZFUITypeDef.h:325
ZFUIMargin operator+(const ZFUIMargin &v0, const ZFUIMargin &v1)
v0 + v1
Definition ZFUITypeDef.h:310
low level string container
Definition zfstring.h:110
zfbool isShared(void) const
whether this string is created from shared
Definition zfstring.h:502
zft_zfstring< T_Char > & assign(const zft_zfstring< T_Char > &s, zfindex len)
replace all content of the string
Definition zfstring.h:362
zfint compare(const zft_zfstring< zfchar > &s) const
Definition zfstring.h:594
zft_zfstring(const zft_zfnullT &dummy)
construct empty string
Definition zfstring.h:183
zfbool capacity(zfindex capacity)
Definition zfstring.h:520
T_Char get(zfindex pos) const
get char at index
Definition zfstring.h:259
void remove(zfindex pos, zfindex len=((zfindex) -1))
remove part of the string
Definition zfstring.h:544
zft_zfstring< T_Char > & assign(const zft_zfstring< T_Char > &s, zfindex offset, zfindex len)
replace all content of the string
Definition zfstring.h:369
zft_zfstring< zfchar > & assign(const zft_zfstring< zfchar > &s)
Definition zfstring.h:357
const T_Char * cString(void) const
access string value, see shared
Definition zfstring.h:494
void swap(zft_zfstring< T_Char > &ref)
swap internal data without deep copy, designed for performance
Definition zfstring.h:275
zft_zfstring< T_Char > & append(const void *s, zfindex len=((zfindex) -1))
append string
Definition zfstring.h:331
void zfunsafe_bufferGiveUp(void *&ret, zfindex &length)
give up the buffer's ownership and return the buffer, you must free it manually by zfunsafe_bufferFre...
Definition zfstring.h:620
zft_zfstring< T_Char > & replace(zfindex replacePos, zfindex replaceLen, const void *s, zfindex len=((zfindex) -1))
replace string in range
Definition zfstring.h:459
zfint compare(const T_Char *s, zfindex len=((zfindex) -1)) const
compare with another string
Definition zfstring.h:598
zft_zfstring< T_Char > & append(const zft_zfstring< T_Char > &s)
append string
Definition zfstring.h:291
const zft_zfstring< T_Char > & sharedCopy(void) const
see shared
Definition zfstring.h:696
void zfunsafe_length(zfindex length)
directly modify the string's length
Definition zfstring.h:651
zft_zfstring(const T_Char *s, zfindex len)
copy content from another string
Definition zfstring.h:163
static void zfunsafe_bufferFree(void *buf)
free buffer returned by zfunsafe_bufferGiveUp
Definition zfstring.h:637
zft_zfstring(const T_Char *s)
copy content from another string
Definition zfstring.h:153
static const zft_zfstring< T_Char > & Empty(void)
global null string ref for impl
Definition zfstring.h:665
T_Char * zfunsafe_buffer(void)
directly access internal writable buffer
Definition zfstring.h:644
zft_zfstring(const zft_zfstring< T_Char > &s)
copy content from another string
Definition zfstring.h:120
zft_zfstring< T_Char > & insert(zfindex insertAt, const zft_zfstring< T_Char > &s)
insert string
Definition zfstring.h:418
void set(zfindex pos, T_Char c)
change char at index
Definition zfstring.h:249
zft_zfstring< T_Char > & append(const zft_zfstring< T_Char > &s, zfindex offset, zfindex len)
append string
Definition zfstring.h:314
zft_zfstring< T_Char > & assign(const zft_zfnullT &dummy)
replace all content of the string
Definition zfstring.h:411
zfbool isEqual(const zft_zfstring< T_Char > &ref) const
true if equal
Definition zfstring.h:510
zft_zfstring(const zft_zfstring< T_Char > &s, zfindex pos, zfindex len)
copy content from another string
Definition zfstring.h:140
zfindex length(void) const
length of the string
Definition zfstring.h:498
zfindex capacity(void) const
get current capacity (including tail '\0')
Definition zfstring.h:529
zft_zfstring< T_Char > & assign(const void *s, zfindex len=((zfindex) -1))
replace all content of the string
Definition zfstring.h:383
zft_zfstring< T_Char > & insert(zfindex insertAt, const void *s, zfindex len=((zfindex) -1))
insert string
Definition zfstring.h:425
void capacityTrim(void)
trim to a proper capacity to save memory
Definition zfstring.h:538
zft_zfstring(const T_Char *s, zfindex pos, zfindex len)
copy content from another string
Definition zfstring.h:173
void removeAll(void)
Definition zfstring.h:562
zft_zfstring< T_Char > & append(const zft_zfstring< T_Char > &s, zfindex len)
append string
Definition zfstring.h:303
const void * buffer(void) const
return internal buffer
Definition zfstring.h:612
zft_zfstring(const zft_zfstring< T_Char > &s, zfindex len)
copy content from another string
Definition zfstring.h:127
zfbool isEqual(const T_Char *s) const
true if equal
Definition zfstring.h:514
static zft_zfstring< T_Char > shared(const void *sLiteral, zfindex length=((zfindex) -1))
explicitly create from literal string
Definition zfstring.h:684
zfbool isEmpty(void) const
true if empty
Definition zfstring.h:506
zft_zfstring(void)
construct an empty string
Definition zfstring.h:113
zft_zfstring< T_Char > & replace(zfindex replacePos, zfindex replaceLen, const zft_zfstring< T_Char > &s)
replace string in range
Definition zfstring.h:451
zft_zfstring< T_Char > & append(T_Char c)
append string
Definition zfstring.h:284
void ZFCoreCapacityOptimize(zfindex &capacity)
util to optimize capacity
Definition zfstring.h:20