Add more string check functions
This commit is contained in:
parent
2cbb897efa
commit
f42fca6350
80
dqn.h
80
dqn.h
@ -355,8 +355,8 @@ DQN_FILE_SCOPE bool dqn_rect_contains_p (DqnRect rect, DqnV2 p);
|
|||||||
////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////
|
||||||
// String Ops
|
// String Ops
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////
|
||||||
DQN_FILE_SCOPE char dqn_char_to_upper (char c);
|
|
||||||
DQN_FILE_SCOPE char dqn_char_to_lower (char c);
|
DQN_FILE_SCOPE char dqn_char_to_lower (char c);
|
||||||
|
DQN_FILE_SCOPE char dqn_char_to_upper (char c);
|
||||||
DQN_FILE_SCOPE bool dqn_char_is_digit (char c);
|
DQN_FILE_SCOPE bool dqn_char_is_digit (char c);
|
||||||
DQN_FILE_SCOPE bool dqn_char_is_alpha (char c);
|
DQN_FILE_SCOPE bool dqn_char_is_alpha (char c);
|
||||||
DQN_FILE_SCOPE bool dqn_char_is_alphanum(char c);
|
DQN_FILE_SCOPE bool dqn_char_is_alphanum(char c);
|
||||||
@ -364,13 +364,17 @@ DQN_FILE_SCOPE bool dqn_char_is_alphanum(char c);
|
|||||||
DQN_FILE_SCOPE i32 dqn_strcmp (const char *a, const char *b);
|
DQN_FILE_SCOPE i32 dqn_strcmp (const char *a, const char *b);
|
||||||
// Returns the length without the null terminator
|
// Returns the length without the null terminator
|
||||||
DQN_FILE_SCOPE i32 dqn_strlen (const char *a);
|
DQN_FILE_SCOPE i32 dqn_strlen (const char *a);
|
||||||
DQN_FILE_SCOPE char *dqn_strncpy(char *dest, const char *src, i32 numChars);
|
DQN_FILE_SCOPE i32 dqn_strlen_delimit_with(const char *a, const char delimiter);
|
||||||
|
DQN_FILE_SCOPE char *dqn_strncpy (char *dest, const char *src, i32 numChars);
|
||||||
|
|
||||||
#define DQN_I32_TO_STR_MAX_BUF_SIZE 11
|
#define DQN_I32_TO_STR_MAX_BUF_SIZE 11
|
||||||
DQN_FILE_SCOPE bool dqn_str_reverse(char *buf, const i32 bufSize);
|
DQN_FILE_SCOPE bool dqn_str_reverse (char *buf, const i32 bufSize);
|
||||||
DQN_FILE_SCOPE i32 dqn_str_to_i32 (const char *const buf, const i32 bufSize);
|
DQN_FILE_SCOPE bool dqn_str_has_substring(const char *const a, const i32 lenA,
|
||||||
|
const char *const b, const i32 lenB);
|
||||||
|
|
||||||
|
DQN_FILE_SCOPE i32 dqn_str_to_i32(const char *const buf, const i32 bufSize);
|
||||||
// Return the len of the derived string
|
// Return the len of the derived string
|
||||||
DQN_FILE_SCOPE i32 dqn_i32_to_str (i32 value, char *buf, i32 bufSize);
|
DQN_FILE_SCOPE i32 dqn_i32_to_str(i32 value, char *buf, i32 bufSize);
|
||||||
|
|
||||||
// Both return the number of bytes read, return 0 if invalid codepoint or UTF8
|
// Both return the number of bytes read, return 0 if invalid codepoint or UTF8
|
||||||
DQN_FILE_SCOPE u32 dqn_ucs_to_utf8(u32 *dest, u32 character);
|
DQN_FILE_SCOPE u32 dqn_ucs_to_utf8(u32 *dest, u32 character);
|
||||||
@ -1600,6 +1604,13 @@ DQN_FILE_SCOPE i32 dqn_strlen(const char *a)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
DQN_FILE_SCOPE i32 dqn_strlen_delimit_with(const char *a, const char delimiter)
|
||||||
|
{
|
||||||
|
i32 result = 0;
|
||||||
|
while (a && a[result] && a[result] != delimiter) result++;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
DQN_FILE_SCOPE char *dqn_strncpy(char *dest, const char *src, i32 numChars)
|
DQN_FILE_SCOPE char *dqn_strncpy(char *dest, const char *src, i32 numChars)
|
||||||
{
|
{
|
||||||
if (!dest) return NULL;
|
if (!dest) return NULL;
|
||||||
@ -1626,6 +1637,65 @@ DQN_FILE_SCOPE bool dqn_str_reverse(char *buf, const i32 bufSize)
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
DQN_FILE_SCOPE bool dqn_str_has_substring(const char *const a, const i32 lenA,
|
||||||
|
const char *const b, const i32 lenB)
|
||||||
|
{
|
||||||
|
if (!a || !b) return false;
|
||||||
|
if (lenA == 0 || lenB == 0) return false;
|
||||||
|
|
||||||
|
const char *longStr, *shortStr;
|
||||||
|
i32 longLen, shortLen;
|
||||||
|
if (lenA > lenB)
|
||||||
|
{
|
||||||
|
longStr = a;
|
||||||
|
longLen = lenA;
|
||||||
|
|
||||||
|
shortStr = b;
|
||||||
|
shortLen = lenB;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
longStr = b;
|
||||||
|
longLen = lenB;
|
||||||
|
|
||||||
|
shortStr = a;
|
||||||
|
shortLen = lenA;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool matchedSubstr = false;
|
||||||
|
for (i32 indexIntoLong = 0; indexIntoLong < longLen && !matchedSubstr;
|
||||||
|
indexIntoLong++)
|
||||||
|
{
|
||||||
|
// NOTE: As we scan through, if the longer string we index into becomes
|
||||||
|
// shorter than the substring we're checking then the substring is not
|
||||||
|
// contained in the long string.
|
||||||
|
i32 remainingLenInLongStr = longLen - indexIntoLong;
|
||||||
|
if (remainingLenInLongStr < shortLen) break;
|
||||||
|
|
||||||
|
const char *longSubstr = &longStr[indexIntoLong];
|
||||||
|
i32 index = 0;
|
||||||
|
for (;;)
|
||||||
|
{
|
||||||
|
if (dqn_char_to_lower(longSubstr[index]) ==
|
||||||
|
dqn_char_to_lower(shortStr[index]))
|
||||||
|
{
|
||||||
|
index++;
|
||||||
|
if (index >= shortLen || !shortStr[index])
|
||||||
|
{
|
||||||
|
matchedSubstr = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return matchedSubstr;
|
||||||
|
}
|
||||||
|
|
||||||
DQN_FILE_SCOPE i32 dqn_str_to_i32(const char *const buf, const i32 bufSize)
|
DQN_FILE_SCOPE i32 dqn_str_to_i32(const char *const buf, const i32 bufSize)
|
||||||
{
|
{
|
||||||
if (!buf || bufSize == 0) return 0;
|
if (!buf || bufSize == 0) return 0;
|
||||||
|
@ -27,6 +27,14 @@ void dqn_strings_test()
|
|||||||
DQN_ASSERT(dqn_char_is_alphanum(' ') == false);
|
DQN_ASSERT(dqn_char_is_alphanum(' ') == false);
|
||||||
DQN_ASSERT(dqn_char_is_alphanum('\n') == false);
|
DQN_ASSERT(dqn_char_is_alphanum('\n') == false);
|
||||||
|
|
||||||
|
DQN_ASSERT(dqn_char_to_lower(L'A') == L'a');
|
||||||
|
DQN_ASSERT(dqn_char_to_lower(L'a') == L'a');
|
||||||
|
DQN_ASSERT(dqn_char_to_lower(L' ') == L' ');
|
||||||
|
|
||||||
|
DQN_ASSERT(dqn_char_to_upper(L'A') == L'A');
|
||||||
|
DQN_ASSERT(dqn_char_to_upper(L'a') == L'A');
|
||||||
|
DQN_ASSERT(dqn_char_to_upper(L' ') == L' ');
|
||||||
|
|
||||||
printf("dqn_strings_test(): char_checks: Completed successfully\n");
|
printf("dqn_strings_test(): char_checks: Completed successfully\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -208,6 +216,36 @@ void dqn_strings_test()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
{
|
||||||
|
|
||||||
|
{
|
||||||
|
char *a = "Microsoft";
|
||||||
|
char *b = "icro";
|
||||||
|
i32 lenA = dqn_strlen(a);
|
||||||
|
i32 lenB = dqn_strlen(b);
|
||||||
|
DQN_ASSERT(dqn_str_has_substring(a, lenA, b, lenB) == true);
|
||||||
|
DQN_ASSERT(dqn_str_has_substring(a, lenA, "iro",
|
||||||
|
dqn_strlen("iro")) == false);
|
||||||
|
DQN_ASSERT(dqn_str_has_substring(b, lenB, a, lenA) == true);
|
||||||
|
DQN_ASSERT(dqn_str_has_substring("iro", dqn_strlen("iro"), a,
|
||||||
|
lenA) == false);
|
||||||
|
DQN_ASSERT(dqn_str_has_substring("", 0, "iro", 4) == false);
|
||||||
|
DQN_ASSERT(dqn_str_has_substring("", 0, "", 0) == false);
|
||||||
|
DQN_ASSERT(dqn_str_has_substring(NULL, 0, NULL, 0) == false);
|
||||||
|
}
|
||||||
|
|
||||||
|
{
|
||||||
|
char *a = "Micro";
|
||||||
|
char *b = "irob";
|
||||||
|
i32 lenA = dqn_strlen(a);
|
||||||
|
i32 lenB = dqn_strlen(b);
|
||||||
|
DQN_ASSERT(dqn_str_has_substring(a, lenA, b, lenB) == false);
|
||||||
|
DQN_ASSERT(dqn_str_has_substring(b, lenB, a, lenA) == false);
|
||||||
|
}
|
||||||
|
|
||||||
|
printf("dqn_strings_test(): str_has_substring: Completed successfully\n");
|
||||||
|
}
|
||||||
|
|
||||||
// UCS <-> UTF8 Checks
|
// UCS <-> UTF8 Checks
|
||||||
{
|
{
|
||||||
// Test ascii characters
|
// Test ascii characters
|
||||||
|
Loading…
Reference in New Issue
Block a user