00001
00012
00013 #include <string.h>
00014
00015 #include "NewtCore.h"
00016 #include "NewtStr.h"
00017
00018
00019
00020 static newtRef NewtParamStr(char * baseStr, size_t baseStrLen, newtRefArg paramStrArray, bool ifthen);
00021 static bool NewtBeginsWith(const char * str, const char * sub);
00022 static bool NewtEndsWith(const char * str, const char * sub);
00023
00024
00025 #pragma mark -
00026
00037 newtRef NewtParamStr(char * baseStr, size_t baseStrLen, newtRefArg paramStrArray, bool ifthen)
00038 {
00039 newtRefVar dstStr;
00040 newtRefVar r;
00041 size_t fpos = 0;
00042 size_t fst = 0;
00043 size_t len;
00044 size_t n;
00045 size_t truePos;
00046 size_t trueLen;
00047 size_t falsePos;
00048 size_t falseLen;
00049 char * found;
00050 char c;
00051
00052 dstStr = NewtMakeString("", false);
00053
00054 do
00055 {
00056 found = memchr(&baseStr[fst], '^', baseStrLen - fst);
00057
00058 if (found == NULL)
00059 break;
00060
00061 c = found[1];
00062
00063 len = found - (baseStr + fpos);
00064 NewtStrCat2(dstStr, &baseStr[fpos], len);
00065 fpos += len;
00066 fst = fpos + 1;
00067
00068 if ('0' <= c && c <= '9')
00069 {
00070 fpos += 2;
00071 fst = fpos;
00072
00073 r = NewtGetArraySlot(paramStrArray, c - '0');
00074
00075 if (NewtRefIsNotNIL(r))
00076 {
00077 NcStrCat(dstStr, r);
00078 }
00079 }
00080 else if (ifthen && c == '?')
00081 {
00082 c = found[2];
00083
00084 if ('0' <= c && c <= '9')
00085 {
00086 n = c - '0';
00087
00088 truePos = fpos + 3;
00089 found = memchr(&baseStr[truePos], '|', baseStrLen - truePos);
00090
00091 if (found != NULL)
00092 {
00093 falsePos = found + 1 - baseStr;
00094 trueLen = falsePos - truePos - 1;
00095
00096 found = memchr(&baseStr[falsePos], '|', baseStrLen - falsePos);
00097
00098 if (found != NULL)
00099 {
00100 fpos = found + 1 - baseStr;
00101 }
00102 else
00103 {
00104 fpos = baseStrLen;
00105 }
00106
00107 falseLen = fpos - falsePos - 1;
00108 }
00109 else
00110 {
00111 trueLen = baseStrLen - truePos;
00112
00113 falsePos = baseStrLen;
00114 falseLen = 0;
00115
00116 fpos = baseStrLen;
00117 }
00118
00119 fst = fpos;
00120
00121 r = NewtGetArraySlot(paramStrArray, n);
00122
00123 if (NewtRefIsNotNIL(r))
00124 {
00125 r = NewtParamStr(&baseStr[truePos], trueLen, paramStrArray, false);
00126 NcStrCat(dstStr, r);
00127 }
00128 else
00129 {
00130 if (falsePos == baseStrLen)
00131 break;
00132
00133 r = NewtParamStr(&baseStr[falsePos], falseLen, paramStrArray, false);
00134 NcStrCat(dstStr, r);
00135 }
00136 }
00137 }
00138 } while(true);
00139
00140 len = baseStrLen - fpos;
00141
00142 if (0 < len)
00143 {
00144 NewtStrCat2(dstStr, &baseStr[fpos], len);
00145 }
00146
00147 return dstStr;
00148 }
00149
00150
00151
00161 bool NewtBeginsWith(const char * str, const char * sub)
00162 {
00163 int32_t len;
00164 int32_t sublen;
00165
00166 len = strlen(str);
00167 sublen = strlen(sub);
00168
00169 if (len < sublen)
00170 return false;
00171 else
00172 return (strncasecmp(str, sub, sublen) == 0);
00173 }
00174
00175
00176
00186 bool NewtEndsWith(const char * str, const char * sub)
00187 {
00188 int32_t st;
00189
00190 st = strlen(str) - strlen(sub);
00191
00192 if (st < 0)
00193 return false;
00194 else
00195 return (strcasecmp(str + st, sub) == 0);
00196 }
00197
00198
00199 #pragma mark -
00200
00211 newtRef NsChr(newtRefArg rcvr, newtRefArg r)
00212 {
00213 if (! NewtRefIsInteger(r))
00214 return NewtThrow(kNErrNotAnInteger, r);
00215
00216 return NewtMakeCharacter(NewtRefToInteger(r));
00217 }
00218
00219
00220
00231 newtRef NsOrd(newtRefArg rcvr, newtRefArg r)
00232 {
00233 if (! NewtRefIsCharacter(r))
00234 return NewtThrow(kNErrNotAnInteger, r);
00235
00236 return NewtMakeInteger(NewtRefToCharacter(r));
00237 }
00238
00239
00240 #pragma mark -
00241
00252 newtRef NsStrLen(newtRefArg rcvr, newtRefArg r)
00253 {
00254 if (! NewtRefIsString(r))
00255 return NewtThrow(kNErrNotAString, r);
00256
00257 return NewtMakeInteger(NewtStringLength(r));
00258 }
00259
00260
00261
00272 newtRef NsSPrintObject(newtRefArg rcvr, newtRefArg r)
00273 {
00274 newtRefVar str;
00275
00276 str = NSSTR("");
00277
00278 NcStrCat(str, r);
00279
00280 return str;
00281 }
00282
00283
00284
00296 newtRef NsSplit(newtRefArg rcvr, newtRefArg r, newtRefArg sep)
00297 {
00298 newtRefVar result;
00299
00300 if (! NewtRefIsString(r))
00301 return NewtThrow(kNErrNotAString, r);
00302
00303 switch (NewtGetRefType(sep, true))
00304 {
00305 case kNewtCharacter:
00306 {
00307 newtRefVar v;
00308 char * next;
00309 char * s;
00310 int c;
00311
00312 s = NewtRefToString(r);
00313 c = NewtRefToCharacter(sep);
00314
00315 result = NewtMakeArray(kNewtRefUnbind, 0);
00316
00317 while (*s)
00318 {
00319 next = strchr(s, c);
00320 if (next == NULL) break;
00321
00322 v = NewtMakeString2(s, next - s, false);
00323 NcAddArraySlot(result, v);
00324 s = next + 1;
00325 }
00326
00327 if (s == NewtRefToString(r))
00328 v = r;
00329 else
00330 v = NSSTR(s);
00331
00332 NcAddArraySlot(result, v);
00333 }
00334 break;
00335
00336 default:
00337 {
00338 newtRefVar initObj[] = {r};
00339
00340 result = NewtMakeArray2(kNewtRefNIL, sizeof(initObj) / sizeof(newtRefVar), initObj);
00341 }
00342 break;
00343 }
00344
00345 return result;
00346 }
00347
00348
00349
00361 newtRef NsParamStr(newtRefArg rcvr, newtRefArg baseString, newtRefArg paramStrArray)
00362 {
00363 if (! NewtRefIsString(baseString))
00364 return NewtThrow(kNErrNotAString, baseString);
00365
00366 if (! NewtRefIsArray(paramStrArray))
00367 return NewtThrow(kNErrNotAnArray, paramStrArray);
00368
00369 return NewtParamStr(NewtRefToString(baseString), NewtStringLength(baseString), paramStrArray, true);
00370 }
00371
00372
00385 newtRef NsSubStr(newtRefArg rcvr, newtRefArg r, newtRefArg start, newtRefArg count)
00386 {
00387 char* theString;
00388 char* theBuffer;
00389 int theStart, theEnd;
00390 size_t theLen;
00391 newtRefVar theResult;
00392
00393 (void) rcvr;
00394
00395
00396 if (! NewtRefIsString(r))
00397 return NewtThrow(kNErrNotAString, r);
00398 if (! NewtRefIsInteger(start))
00399 return NewtThrow(kNErrNotAnInteger, start);
00400
00401 theString = NewtRefToString(r);
00402 theLen = strlen(theString);
00403
00404 theStart = NewtRefToInteger(start);
00405
00406 if (!NewtRefIsNIL(count))
00407 {
00408 if (!NewtRefIsInteger(count))
00409 {
00410 return NewtThrow(kNErrNotAnInteger, count);
00411 }
00412 theEnd = theStart + NewtRefToInteger(count);
00413 if (theEnd > theLen)
00414 {
00415 return NewtThrow(kNErrOutOfRange, count);
00416 }
00417 } else {
00418 theEnd = theLen;
00419 }
00420
00421
00422 theLen = theEnd - theStart;
00423
00424
00425 theBuffer = (char*) malloc(theLen + 1);
00426 (void) memcpy(theBuffer, (const char*) &theString[theStart], theLen);
00427 theBuffer[theLen] = 0;
00428 theResult = NewtMakeString(theBuffer, false);
00429 free(theBuffer);
00430
00431 return theResult;
00432 }
00433
00434
00444 newtRef NsStrEqual(newtRefArg rcvr, newtRefArg a, newtRefArg b)
00445 {
00446 char* aString;
00447 char* bString;
00448 newtRefVar theResult = kNewtRefNIL;
00449
00450 (void) rcvr;
00451
00452
00453 if (! NewtRefIsString(a))
00454 {
00455 theResult = NewtThrow(kNErrNotAString, a);
00456 } else if (! NewtRefIsString(b)) {
00457 theResult = NewtThrow(kNErrNotAString, b);
00458 } else if (a == b) {
00459 theResult = kNewtRefTRUE;
00460 } else {
00461 aString = NewtRefToString(a);
00462 bString = NewtRefToString(b);
00463
00464 if (strcasecmp(aString, bString) == 0)
00465 {
00466 theResult = kNewtRefTRUE;
00467 }
00468 }
00469
00470 return theResult;
00471 }
00472
00473
00485 newtRef NsStrExactCompare(newtRefArg rcvr, newtRefArg a, newtRefArg b)
00486 {
00487 char* aString;
00488 char* bString;
00489 newtRefVar theResult;
00490
00491 (void) rcvr;
00492
00493
00494 if (! NewtRefIsString(a))
00495 {
00496 theResult = NewtThrow(kNErrNotAString, a);
00497 } else if (! NewtRefIsString(b)) {
00498 theResult = NewtThrow(kNErrNotAString, b);
00499 } else if (a == b) {
00500 theResult = NewtMakeInteger(0);
00501 } else {
00502 aString = NewtRefToString(a);
00503 bString = NewtRefToString(b);
00504
00505 theResult = NewtMakeInteger(strcmp(aString, bString));
00506 }
00507
00508 return theResult;
00509 }
00510
00511
00512
00523 newtRef NsBeginsWith(newtRefArg rcvr, newtRefArg str, newtRefArg sub)
00524 {
00525 bool result;
00526
00527 if (! NewtRefIsString(str))
00528 return NewtThrow(kNErrNotAString, str);
00529
00530 if (! NewtRefIsString(sub))
00531 return NewtThrow(kNErrNotAString, sub);
00532
00533 result = NewtBeginsWith(NewtRefToString(str), NewtRefToString(sub));
00534
00535 return NewtMakeBoolean(result);
00536 }
00537
00538
00539
00550 newtRef NsEndsWith(newtRefArg rcvr, newtRefArg str, newtRefArg sub)
00551 {
00552 bool result;
00553
00554 if (! NewtRefIsString(str))
00555 return NewtThrow(kNErrNotAString, str);
00556
00557 if (! NewtRefIsString(sub))
00558 return NewtThrow(kNErrNotAString, sub);
00559
00560 result = NewtEndsWith(NewtRefToString(str), NewtRefToString(sub));
00561
00562 return NewtMakeBoolean(result);
00563 }
00564