19 static inline int _max(
int x,
int y)
25 void WvFastString::setsize(
size_t i)
51 void WvFastString::construct(
const char *_str)
71 link(&nullbuf, s.str);
82 size_t l = retval.len();
83 retval.str += (i < l ? i : l);
88 WvString::WvString(
const char *_str)
98 inline static char *wv_uitoar(
char *begin, T i)
113 case 0: *end++ =
'0';
break;
114 case 1: *end++ =
'1';
break;
115 case 2: *end++ =
'2';
break;
116 case 3: *end++ =
'3';
break;
117 case 4: *end++ =
'4';
break;
118 case 5: *end++ =
'5';
break;
119 case 6: *end++ =
'6';
break;
120 case 7: *end++ =
'7';
break;
121 case 8: *end++ =
'8';
break;
122 case 9: *end++ =
'9';
break;
135 template <
typename T>
136 inline static char *wv_itoar(
char *begin, T i)
141 bool negative =
false;
147 char *end = wv_uitoar(begin, i);
157 inline static void wv_strrev(
char *begin,
char *end)
181 wv_strrev(str, wv_itoar(str, i));
188 wv_strrev(str, wv_uitoar(str, i));
195 wv_strrev(str, wv_itoar(str, i));
202 wv_strrev(str, wv_uitoar(str, i));
209 wv_strrev(str, wv_itoar(str, i));
216 wv_strrev(str, wv_uitoar(str, i));
223 wv_strrev(str, wv_itoar(str, i));
230 wv_strrev(str, wv_uitoar(str, i));
237 sprintf(str,
"%g", i);
241 WvFastString::~WvFastString()
247 void WvFastString::unlink()
249 if (buf && ! --buf->links)
257 void WvFastString::link(
WvStringBuf *_buf,
const char *_str)
269 (WVSTRINGBUF_SIZE(buf) + size + WVSTRING_EXTRA) | 3);
290 size_t WvFastString::len()
const 292 return str ? strlen(str) : 0;
296 void WvFastString::newbuf(
size_t size)
308 if (!is_unique() && str)
311 memcpy(newb->data, str, newb->size);
313 link(newb, newb->data);
322 return (buf->links <= 1);
328 if (s2.buf == buf && s2.str == str)
333 link(s2.buf, s2.str);
339 WvString &WvString::operator= (
int i)
343 sprintf(str,
"%d", i);
350 if (s2.str == str && (!s2.buf || s2.buf == buf))
355 if (str && buf && buf->links == 1)
359 buf->size = strlen(str);
361 if (str < s2.str && s2.str <= (str + buf->size))
365 memmove(buf->data, s2.str, buf->size);
371 link(&nullbuf, s2.str);
378 link(s2.buf, s2.str);
387 return (str==s2.str) || (str && s2.str && !strcmp(str, s2.str));
393 return (str!=s2.str) && (!str || !s2.str || strcmp(str, s2.str));
399 if (str == s2.str)
return false;
400 if (str == 0)
return true;
401 if (s2.str == 0)
return false;
402 return strcmp(str, s2.str) < 0;
406 bool WvFastString::operator== (
const char *s2)
const 408 return (str==s2) || (str && s2 && !strcmp(str, s2));
412 bool WvFastString::operator!= (
const char *s2)
const 414 return (str!=s2) && (!str || !s2 || strcmp(str, s2));
418 bool WvFastString::operator< (
const char *s2)
const 420 if (str == s2)
return false;
421 if (str == 0)
return true;
422 if (s2 == 0)
return false;
423 return strcmp(str, s2) < 0;
430 return !str || !str[0];
445 static const char *pparse(
const char *cptr,
bool &zeropad,
446 int &justify,
int &maxlen,
int &argnum)
448 assert(*cptr ==
'%');
451 zeropad = (*cptr ==
'0');
453 justify = atoi(cptr);
455 for (; *cptr && *cptr!=
'.' && *cptr!=
'%' && *cptr!=
'$' 456 && !isalpha(*cptr); cptr++)
458 if (!*cptr)
return cptr;
461 maxlen = atoi(cptr+1);
465 for (; *cptr && *cptr!=
'%' && *cptr!=
'$' && !isalpha(*cptr); cptr++)
467 if (!*cptr)
return cptr;
470 argnum = atoi(cptr+1);
474 for (; *cptr && *cptr!=
'%' && !isalpha(*cptr); cptr++)
500 static const char blank[] =
"(nil)";
503 const char *iptr = format, *arg;
505 int total = 0, aplen, ladd, justify, maxlen, argnum;
520 iptr = pparse(iptr, zeropad, justify, maxlen, argnum);
528 assert(*iptr ==
's' || *iptr ==
'c');
532 argP = (argnum > 0 ) ? (argv + argnum -1): argptr;
533 if (!*argP || !(**argP).
cstr())
536 arg = (**argP).
cstr();
537 ladd = _max(abs(justify), strlen(arg));
538 if (maxlen && maxlen < ladd)
555 output.setsize(total + 1);
571 iptr = pparse(iptr, zeropad, justify, maxlen, argnum);
579 argP = (argnum > 0 ) ? (argv + argnum -1): argptr;
580 if (!*argP || !(**argP).
cstr())
583 arg = (**argP).
cstr();
585 if (maxlen && maxlen < aplen)
591 memset(optr,
'0', justify-aplen);
593 memset(optr,
' ', justify-aplen);
594 optr += justify-aplen;
597 strncpy(optr, arg, aplen);
600 if (justify < 0 && -justify > aplen)
603 memset(optr,
'0', -justify-aplen);
605 memset(optr,
' ', -justify-aplen);
606 optr += -justify - aplen;
616 argP = (argnum > 0 ) ? (argv + argnum -1): argptr++;
617 if (!*argP || !(**argP))
621 *optr++ = (char)atoi(arg);
A WvFastString acts exactly like a WvString, but can take (const char *) strings without needing to a...
WvFastString offset(size_t i) const
Returns a copy of string pointed i bytes into this.
WvString & unique()
make the buf and str pointers owned only by this WvString.
const char * cstr() const
return a (const char *) for this string.
bool is_unique() const
returns true if this string is already unique()
bool operator!() const
the not operator is 'true' if string is empty
WvFastString()
Create an empty, NULL string.
WvString is an implementation of a simple and efficient printable-string class.
static void do_format(WvFastString &output, const char *format, const WvFastString *const *a)
when this is called, we assume output.str == NULL; it will be filled.