summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorTyge Løvset <[email protected]>2021-05-21 10:12:32 +0200
committerTyge Løvset <[email protected]>2021-05-21 10:12:32 +0200
commit141c31a725ef0509998b208f4dda897347cbe4f2 (patch)
tree0b14e1b9b4e6ca8b7b0efc3c4b2ebfd87b3e035c
parentbbd74bed602b8459c4dfe785263725c9bfe84e45 (diff)
downloadSTC-modified-141c31a725ef0509998b208f4dda897347cbe4f2.tar.gz
STC-modified-141c31a725ef0509998b208f4dda897347cbe4f2.zip
Updated string split / tokenizer example in csview docs.
-rw-r--r--docs/ccommon_api.md100
-rw-r--r--docs/csview_api.md56
-rw-r--r--include/stc/csview.h10
3 files changed, 95 insertions, 71 deletions
diff --git a/docs/ccommon_api.md b/docs/ccommon_api.md
index 916f9780..6ccec29e 100644
--- a/docs/ccommon_api.md
+++ b/docs/ccommon_api.md
@@ -2,59 +2,12 @@
The following handy macros are safe to use, i.e. have no side-effects.
-### c_var, c_emplace
-**c_var** declares and initializes any container with an array of elements. **c_emplace** adds elements to any existing container:
-```c
-c_var (cvec_i, vec, {1, 2, 3}); // declare and emplace
-c_emplace(cvec_i, vec, {4, 5, 6}); // adds to existing vec
-```
-
-### c_forrange
-Declare an iterator and specify a range to iterate with a for loop. Like python's ***for i in range()*** loop:
-
-| Usage | Python equivalent |
-|:----------------------------------------------|:-------------------------------------|
-| `c_forrange (stop)` | `for _ in range(stop):` |
-| `c_forrange (i, stop) // IterType = size_t` | `for i in range(stop):` |
-| `c_forrange (i, IterType, stop)` | `for i in range(stop):` |
-| `c_forrange (i, IterType, start, stop)` | `for i in range(start, stop):` |
-| `c_forrange (i, IterType, start, stop, step)` | `for i in range(start, stop, step):` |
-
-```c
-c_forrange (5) printf("x");
-// xxxxx
-c_forrange (i, 5) printf(" %zu", i);
-// 0 1 2 3 4
-c_forrange (i, int, -3, 3) printf(" %d", i);
-// -3 -2 -1 0 1 2
-c_forrange (i, int, 30, 0, -5) printf(" %d", i);
-// 30 25 20 15 10 5
-```
-
-### c_foreach
-
-| Usage | Description |
-|:-------------------------------------|:-----------------------------|
-| `c_foreach (it, ctype, container)` | Iteratate all elements |
-| `c_foreach (it, ctype, it1, it2)` | Iterate the range [it1, it2) |
-
-```c
-using_csset(x, int);
-...
-c_var (csset_x, set, {23, 3, 7, 5, 12});
-c_foreach (i, csset_x, set) printf(" %d", *i.ref);
-// 3 5 7 12 23
-csset_x_iter_t it = csset_x_find(&set, 7);
-c_foreach (i, csset_x, it, csset_x_end(&set)) printf(" %d", *i.ref);
-// 7 12 23
-```
-
### c_defer, c_with, c_withvar, c_withbuf, c_breakwith
-General defer mechanics. These macros allows to specify destructors explicitly or implicitly where the
+General *defer* mechanics. These macros allows to specify destructors explicitly or implicitly where the
constructors are defined. This ensures that resources are released after usage, and avoids memory leaks.
+**c_with / c_withvar** are inspired by Python's *with* statement.
-**NB**: ***Only*** use `c_breakwith` to break out of the `c_with`-block if needed. ***Never*** use `return`,
-`break`, or `goto` inside the block.
+**NB**: ***Only*** use `c_breakwith` or `c_breakdefer` to break out of `c_with`/`c_defer`-blocks. ***Never*** use `return`, `break`, or `goto` inside such a block.
| Usage | Description |
|:---------------------------------|:--------------------------------------------------|
@@ -97,6 +50,53 @@ int main()
}
```
+### c_foreach
+
+| Usage | Description |
+|:-------------------------------------|:-----------------------------|
+| `c_foreach (it, ctype, container)` | Iteratate all elements |
+| `c_foreach (it, ctype, it1, it2)` | Iterate the range [it1, it2) |
+
+```c
+using_csset(x, int);
+...
+c_var (csset_x, set, {23, 3, 7, 5, 12});
+c_foreach (i, csset_x, set) printf(" %d", *i.ref);
+// 3 5 7 12 23
+csset_x_iter_t it = csset_x_find(&set, 7);
+c_foreach (i, csset_x, it, csset_x_end(&set)) printf(" %d", *i.ref);
+// 7 12 23
+```
+
+### c_forrange
+Declare an iterator and specify a range to iterate with a for loop. Like python's ***for i in range()*** loop:
+
+| Usage | Python equivalent |
+|:----------------------------------------------|:-------------------------------------|
+| `c_forrange (stop)` | `for _ in range(stop):` |
+| `c_forrange (i, stop) // IterType = size_t` | `for i in range(stop):` |
+| `c_forrange (i, IterType, stop)` | `for i in range(stop):` |
+| `c_forrange (i, IterType, start, stop)` | `for i in range(start, stop):` |
+| `c_forrange (i, IterType, start, stop, step)` | `for i in range(start, stop, step):` |
+
+```c
+c_forrange (5) printf("x");
+// xxxxx
+c_forrange (i, 5) printf(" %zu", i);
+// 0 1 2 3 4
+c_forrange (i, int, -3, 3) printf(" %d", i);
+// -3 -2 -1 0 1 2
+c_forrange (i, int, 30, 0, -5) printf(" %d", i);
+// 30 25 20 15 10 5
+```
+
+### c_var, c_emplace
+**c_var** declares and initializes any container with an array of elements. **c_emplace** adds elements to any existing container:
+```c
+c_var (cvec_i, vec, {1, 2, 3}); // declare and emplace
+c_emplace(cvec_i, vec, {4, 5, 6}); // adds to existing vec
+```
+
### c_new, c_new_n, c_del, c_make
| Usage | Meaning |
diff --git a/docs/csview_api.md b/docs/csview_api.md
index 9b399202..0a4595e0 100644
--- a/docs/csview_api.md
+++ b/docs/csview_api.md
@@ -90,12 +90,8 @@ uint64_t csview_hash_ref(const csview* x, size_t ignored);
| `c_lit(literal)` | csview constructor | `sview = c_lit("hello, world");` |
| `csview_ARG(sv)` | printf argument | `printf("%.*s", csview_ARG(sv));` |
-## Container adaptors
+## Associative cstr-containers with csview emplace/lookup API
```
-using_cvec_sv()
-using_cdeq_sv()
-using_clist_sv()
-
using_csmap_svkey(X, Mapped)
using_csmap_svkey(X, Mapped, mappedDel)
using_csmap_svkey(X, Mapped, mappedDel, mappedClone)
@@ -169,26 +165,62 @@ Last element
world: 200
```
+
### Example 2: csview tokenizer (string split)
-Splits strings into tokens. **No** memory allocations, *strlen()*, or string zero-termination dependency.
+Splits strings into tokens. *print_split()* makes **no** memory allocations, *strlen()* calls, or has null-terminated string dependency. *string_split()* returns a cstr vector.
```c
#include <stc/csview.h>
+#include <stc/cvec.h>
+
+void print_split(csview str, csview sep)
+{
+ csview token = csview_first_token(str, sep);
+ for (;;) {
+ // print non-null-terminated csview
+ printf("\"%.*s\"\n", csview_ARG(token));
+ if (csview_end(&token).ref == csview_end(&str).ref) break;
+ token = csview_next_token(str, sep, token);
+ }
+}
+
+using_cvec_str();
-void splitstring(csview str, csview sep)
+cvec_str string_split(csview str, csview sep)
{
+ cvec_str vec = cvec_str_init();
csview token = csview_first_token(str, sep);
for (;;) {
- printf("token: \"%.*s\"\n", csview_ARG(token));
+ cvec_str_push_back(&vec, cstr_from_v(token));
if (csview_end(&token).ref == csview_end(&str).ref) break;
token = csview_next_token(str, sep, token);
}
- puts("--");
+ return vec;
}
int main()
{
- splitstring(c_lit("//This is//double slash//separated//string"), c_lit("//"));
- splitstring(c_lit("This has no matching separator"), c_lit("xx"));
- splitstring(c_lit("Split,this,string,now,ok,"), c_lit(","));
+ print_split(c_lit("//This is a//double-slash//separated//string"), c_lit("//")); puts("");
+ print_split(c_lit("This has no matching separator"), c_lit("xx")); puts("");
+
+ c_with (cvec_str v = string_split(c_lit("Split,this,,string,now,"), c_lit(",")), cvec_str_del(&v))
+ c_foreach (i, cvec_str, v)
+ printf("\"%s\"\n", i.ref->str);
}
```
+Output:
+```
+""
+"This is a"
+"double-slash"
+"separated"
+"string"
+
+"This has no matching separator"
+
+"Split"
+"this"
+""
+"string"
+"now"
+""
+```
diff --git a/include/stc/csview.h b/include/stc/csview.h
index 7111471b..2e52ad73 100644
--- a/include/stc/csview.h
+++ b/include/stc/csview.h
@@ -128,15 +128,7 @@ STC_INLINE bool csview_equals_ref(const csview* a, const csview* b)
{ return a->size == b->size && !memcmp(a->str, b->str, a->size); }
#define csview_hash_ref(xp, none) c_default_hash((xp)->str, (xp)->size)
-/* ---- Containers ---- */
-
-#define using_cvec_sv() \
- using_cvec(sv, cstr, csview_compare_ref, cstr_del, cstr_from_v, cstr_to_v, csview)
-#define using_cdeq_sv() \
- using_cdeq(sv, cstr, csview_compare_ref, cstr_del, cstr_from_v, cstr_to_v, csview)
-#define using_clist_sv() \
- using_clist(sv, cstr, csview_compare_ref, cstr_del, cstr_from_v, cstr_to_v, csview)
-
+/* ---- Associative cstr-containers with csview emplace/lookup API ---- */
#define using_csmap_svkey(...) c_MACRO_OVERLOAD(using_csmap_svkey, __VA_ARGS__)