Tue, 27 Oct 2015 15:29:34 +0100
added sstrstr() function + improved sstrsplit variants by using sstrprefix()
test/main.c | file | annotate | diff | comparison | revisions | |
test/string_tests.c | file | annotate | diff | comparison | revisions | |
test/string_tests.h | file | annotate | diff | comparison | revisions | |
ucx/string.c | file | annotate | diff | comparison | revisions | |
ucx/string.h | file | annotate | diff | comparison | revisions |
1.1 --- a/test/main.c Mon Oct 26 14:09:45 2015 +0100 1.2 +++ b/test/main.c Tue Oct 27 15:29:34 2015 +0100 1.3 @@ -125,6 +125,7 @@ 1.4 ucx_test_register(suite, test_sstrcasecmp); 1.5 ucx_test_register(suite, test_sstrcat); 1.6 ucx_test_register(suite, test_sstrchr_sstrrchr); 1.7 + ucx_test_register(suite, test_sstrstr); 1.8 ucx_test_register(suite, test_sstrsplit); 1.9 ucx_test_register(suite, test_sstrtrim); 1.10 ucx_test_register(suite, test_sstrprefixsuffix);
2.1 --- a/test/string_tests.c Mon Oct 26 14:09:45 2015 +0100 2.2 +++ b/test/string_tests.c Tue Oct 27 15:29:34 2015 +0100 2.3 @@ -79,6 +79,27 @@ 2.4 UCX_TEST_END 2.5 } 2.6 2.7 +UCX_TEST(test_sstrstr) { 2.8 + sstr_t str = ST("find the match in this string"); 2.9 + UCX_TEST_BEGIN 2.10 + 2.11 + sstr_t notfound = sstrstr(str, S("no match")); 2.12 + UCX_TEST_ASSERT(notfound.length == 0, "no match must return empty string"); 2.13 + 2.14 + sstr_t result = sstrstr(str, S("match")); 2.15 + UCX_TEST_ASSERT(result.length == 20, "sstrstr returned wrong length"); 2.16 + UCX_TEST_ASSERT(!strcmp("match in this string", result.ptr), 2.17 + "sstrstr did not return the expected string"); 2.18 + 2.19 + result = sstrstr(str, S("")); 2.20 + UCX_TEST_ASSERT(result.length == str.length, 2.21 + "sstrstr with empty match string returned wrong length"); 2.22 + UCX_TEST_ASSERT(!strcmp(str.ptr, result.ptr), 2.23 + "sstrstr with empty match string did not return the original string"); 2.24 + 2.25 + UCX_TEST_END 2.26 +} 2.27 + 2.28 UCX_TEST(test_sstrcmp) { 2.29 sstr_t str = ST("compare this"); 2.30
3.1 --- a/test/string_tests.h Mon Oct 26 14:09:45 2015 +0100 3.2 +++ b/test/string_tests.h Tue Oct 27 15:29:34 2015 +0100 3.3 @@ -42,6 +42,7 @@ 3.4 UCX_TEST(test_sstrcasecmp); 3.5 UCX_TEST(test_sstrcat); 3.6 UCX_TEST(test_sstrchr_sstrrchr); 3.7 +UCX_TEST(test_sstrstr); 3.8 UCX_TEST(test_sstrsplit); 3.9 UCX_TEST(test_sstrtrim); 3.10 UCX_TEST(test_sstrprefixsuffix);
4.1 --- a/ucx/string.c Mon Oct 26 14:09:45 2015 +0100 4.2 +++ b/ucx/string.c Tue Oct 27 15:29:34 2015 +0100 4.3 @@ -175,6 +175,24 @@ 4.4 return n; 4.5 } 4.6 4.7 +sstr_t sstrstr(sstr_t string, sstr_t match) { 4.8 + if (match.length == 0) { 4.9 + return string; 4.10 + } 4.11 + 4.12 + for (size_t i = 0 ; i < string.length ; i++) { 4.13 + sstr_t substr = sstrsubs(string, i); 4.14 + if (sstrprefix(substr, match)) { 4.15 + return substr; 4.16 + } 4.17 + } 4.18 + 4.19 + sstr_t emptystr; 4.20 + emptystr.length = 0; 4.21 + emptystr.ptr = NULL; 4.22 + return emptystr; 4.23 +} 4.24 + 4.25 sstr_t* sstrsplit(sstr_t s, sstr_t d, ssize_t *n) { 4.26 return sstrsplit_a(ucx_default_allocator(), s, d, n); 4.27 } 4.28 @@ -201,23 +219,13 @@ 4.29 } 4.30 4.31 for (size_t i = 0 ; i < s.length ; i++) { 4.32 - if (sv.ptr[i] == d.ptr[0]) { 4.33 - _Bool match = 1; 4.34 - for (size_t j = 1 ; j < d.length ; j++) { 4.35 - if (j+i < s.length) { 4.36 - match &= (sv.ptr[i+j] == d.ptr[j]); 4.37 - } else { 4.38 - match = 0; 4.39 - break; 4.40 - } 4.41 + sstr_t substr = sstrsubs(sv, i); 4.42 + if (sstrprefix(substr, d)) { 4.43 + (*n)++; 4.44 + for (size_t j = 0 ; j < d.length ; j++) { 4.45 + sv.ptr[i+j] = 0; 4.46 } 4.47 - if (match) { 4.48 - (*n)++; 4.49 - for (size_t j = 0 ; j < d.length ; j++) { 4.50 - sv.ptr[i+j] = 0; 4.51 - } 4.52 - i += d.length - 1; // -1, because the loop will do a i++ 4.53 - } 4.54 + i += d.length - 1; // -1, because the loop will do a i++ 4.55 } 4.56 if ((*n) == nmax) break; 4.57 }
5.1 --- a/ucx/string.h Mon Oct 26 14:09:45 2015 +0100 5.2 +++ b/ucx/string.h Tue Oct 27 15:29:34 2015 +0100 5.3 @@ -214,6 +214,23 @@ 5.4 sstr_t sstrrchr(sstr_t string, int chr); 5.5 5.6 /** 5.7 + * Returns a substring starting at the location of the first occurrence of the 5.8 + * specified string. 5.9 + * 5.10 + * If the string does not contain the other string, an empty string is returned. 5.11 + * 5.12 + * If <code>match</code> is an empty string, the complete <code>string</code> is 5.13 + * returned. 5.14 + * 5.15 + * @param string the string to be scanned 5.16 + * @param match string containing the sequence of characters to match 5.17 + * @return a substring starting at the first occurrence of 5.18 + * <code>match</code>, or an empty string, if the sequence is not 5.19 + * present in <code>string</code> 5.20 + */ 5.21 +sstr_t sstrstr(sstr_t string, sstr_t match); 5.22 + 5.23 +/** 5.24 * Splits a string into parts by using a delimiter string. 5.25 * 5.26 * This function will return <code>NULL</code>, if one of the following happens: