summaryrefslogtreecommitdiffhomepage
path: root/README.md
diff options
context:
space:
mode:
author_Tradam <[email protected]>2023-09-08 01:29:47 +0000
committerGitHub <[email protected]>2023-09-08 01:29:47 +0000
commit3c76c7f3d5db3f9586a90d03f8fbb02d79de9acd (patch)
treeafbe4b540967223911f7c5de36559b82154f02f3 /README.md
parent0841165881871ee01b782129be681209aeed2423 (diff)
parent1a72205fe05c2375cfd380dd8381a8460d9ed8d1 (diff)
downloadSTC-modified-modified.tar.gz
STC-modified-modified.zip
Merge branch 'stclib:master' into modifiedHEADmodified
Diffstat (limited to 'README.md')
-rw-r--r--README.md293
1 files changed, 178 insertions, 115 deletions
diff --git a/README.md b/README.md
index 65d00324..d99d8a76 100644
--- a/README.md
+++ b/README.md
@@ -3,8 +3,8 @@
STC - Smart Template Containers
===============================
-### [Version 4.2](#version-history)
-
+### [Version 4.3 Pre-release](#version-history)
+- See details for breaking changes.
---
Description
-----------
@@ -18,25 +18,26 @@ Containers
- [***cbox*** - **std::unique_ptr** alike type](docs/cbox_api.md)
- [***cbits*** - **std::bitset** alike type](docs/cbits_api.md)
- [***clist*** - **std::forward_list** alike type](docs/clist_api.md)
+- [***cstack*** - **std::stack** alike type](docs/cstack_api.md)
+- [***cvec*** - **std::vector** alike type](docs/cvec_api.md)
- [***cqueue*** - **std::queue** alike type](docs/cqueue_api.md)
+- [***cdeq*** - **std::deque** alike type](docs/cdeq_api.md)
- [***cpque*** - **std::priority_queue** alike type](docs/cpque_api.md)
- [***cmap*** - **std::unordered_map** alike type](docs/cmap_api.md)
- [***cset*** - **std::unordered_set** alike type](docs/cset_api.md)
- [***csmap*** - **std::map** sorted map alike type](docs/csmap_api.md)
- [***csset*** - **std::set** sorted set alike type](docs/csset_api.md)
-- [***cstack*** - **std::stack** alike type](docs/cstack_api.md)
- [***cstr*** - **std::string** alike type](docs/cstr_api.md)
- [***csview*** - **std::string_view** alike type](docs/csview_api.md)
-- [***cspan*** - **std::span/std::mdspan** alike type](docs/cspan_api.md)
-- [***cdeq*** - **std::deque** alike type](docs/cdeq_api.md)
-- [***cvec*** - **std::vector** alike type](docs/cvec_api.md)
+- [***crawstr*** - null-terminated string view type](docs/crawstr_api.md)
+- [***cspan*** - **std::span** + **std::mdspan** alike type](docs/cspan_api.md)
Algorithms
----------
-- [***Ranged for-loops*** - c_foreach, c_forpair, c_forlist](docs/ccommon_api.md#ranged-for-loops)
-- [***Range algorithms*** - c_forrange, crange, c_forfilter](docs/ccommon_api.md#range-algorithms)
-- [***Generic algorithms*** - c_make, c_find_if, c_erase_if, csort, etc.](docs/ccommon_api.md#generic-algorithms)
-- [***Coroutines*** - Simon Tatham's coroutines done right.](docs/ccommon_api.md#coroutines)
+- [***Ranged for-loops*** - c_foreach, c_forpair, c_forlist](docs/algorithm_api.md#ranged-for-loops)
+- [***Range algorithms*** - c_forrange, crange, c_forfilter](docs/algorithm_api.md#range-algorithms)
+- [***Generic algorithms*** - c_init, c_find_if, c_erase_if, csort, etc.](docs/algorithm_api.md#generic-algorithms)
+- [***Coroutines*** - ergonomic portable coroutines](docs/coroutine_api.md)
- [***Regular expressions*** - Rob Pike's Plan 9 regexp modernized!](docs/cregex_api.md)
- [***Random numbers*** - a very fast *PRNG* based on *SFC64*](docs/crandom_api.md)
- [***Command line argument parser*** - similar to *getopt()*](docs/coption_api.md)
@@ -61,15 +62,14 @@ List of contents
---
## Highlights
-- **No boilerplate code** - Specify only the required template parameters, e.g. ***cmp***- and/or ***clone***-, ***drop***- functions, and leave the rest as defaults.
+- **Minimal boilerplate code** - Specify only the required template parameters, and leave the rest as defaults.
- **Fully type safe** - Because of templating, it avoids error-prone casting of container types and elements back and forth from the containers.
-- **User friendly** - Just include the headers and you are good. The API and functionality is very close to c++ STL and is fully listed in the docs.
-- **Unparalleled performance** - Maps and sets are much faster than the C++ STL containers, the remaining are similar in speed.
+- **High performance** - Unordered maps and sets, queues and deques are significantly faster than the C++ STL containers, the remaining are similar or close to STL in speed (See graph below).
- **Fully memory managed** - Containers destructs keys/values via default or user supplied drop function. They may be cloned if element types are clonable. Also, smart pointers are supported and can be stored in containers. See [***carc***](docs/carc_api.md) and [***cbox***](docs/cbox_api.md).
-- **Uniform, easy-to-learn API** - Intuitive method/type names and uniform usage across the various containers.
+- **Uniform, easy-to-learn API** - Just include the headers and you are good. The API and functionality resembles c++ STL and is fully listed in the docs. Intuitive method/type names and uniform usage across the various containers.
- **No signed/unsigned mixing** - Unsigned sizes and indices mixed with signed for comparison and calculation is asking for trouble. STC only uses signed numbers in the API for this reason.
- **Small footprint** - Small source code and generated executables. The executable from the example below using *four different* container types is only ***19 Kb in size*** compiled with gcc -O3 -s on Linux.
-- **Dual mode compilation** - By default it is a simple header-only library with inline and static methods only, but you can easily switch to create a traditional library with shared symbols, without changing existing source files. See the Installation section.
+- **Dual mode compilation** - By default it is a simple header-only library with inline and static methods only, but you can easily switch to create a traditional library with shared symbols, without changing existing source files. See the [installation section](#installation).
- **No callback functions** - All passed template argument functions/macros are directly called from the implementation, no slow callbacks which requires storage.
- **Compiles with C++ and C99** - C code can be compiled with C++ (container element types must be POD).
- **Forward declaration** - Templated containers may be [forward declared](#forward-declarations) without including the full API/implementation.
@@ -81,9 +81,9 @@ List of contents
1. ***Centralized analysis of template parameters***. The analyser assigns values to all
non-specified template parameters (based on the specified ones) using meta-programming, so
that you don't have to! You may specify a set of "standard" template parameters for each
-container, but as a minimum *only one is required*: `i_val` (+ `i_key` for maps). In this
+container, but as a minimum *only one is required*: `i_key` (+ `i_val` for maps). In this
case, STC assumes that the elements are of basic types. For non-trivial types, additional
-template parameters must be given.
+template parameters must be given.
2. ***Alternative insert/lookup type***. You may specify an alternative type to use for
lookup in containers. E.g., containers with STC string elements (**cstr**) uses `const char*`
as lookup type, so constructing a `cstr` (which may allocate memory) for the lookup
@@ -95,21 +95,21 @@ So instead of calling e.g. `cvec_str_push(&vec, cstr_from("Hello"))`, you may ca
same element access syntax. E.g.:
- `c_foreach (it, MyInts, myints) *it.ref += 42;` works for any container defined as
`MyInts` with `int` elements.
- - `c_foreach (it, MyInts, it1, it2) *it.ref += 42;` iterates from `it1` up to `it2`.
+ - `c_foreach (it, MyInts, it1, it2) *it.ref += 42;` iterates from `it1` up to not including `it2`.
---
## Performance
STC is a fast and memory efficient library, and code compiles fast:
-![Benchmark](misc/benchmarks/pics/benchmark.gif)
+![Benchmark](docs/pics/Figure_1.png)
Benchmark notes:
-- The barchart shows average test times over three platforms: Mingw64 10.30, Win-Clang 12, VC19. CPU: Ryzen 7 2700X CPU @4Ghz.
+- The barchart shows average test times over three compilers: **Mingw64 13.1.0, Win-Clang 16.0.5, VC-19-36**. CPU: **Ryzen 7 5700X**.
- Containers uses value types `uint64_t` and pairs of `uint64_t` for the maps.
- Black bars indicates performance variation between various platforms/compilers.
-- Iterations are repeated 4 times over n elements.
-- **find()**: not executed for *forward_list*, *deque*, and *vector* because these c++ containers does not have native *find()*.
+- Iterations and access are repeated 4 times over n elements.
+- access: no entryfor *forward_list*, *deque*, and *vector* because these c++ containers does not have native *find()*.
- **deque**: *insert*: n/3 push_front(), n/3 push_back()+pop_front(), n/3 push_back().
- **map and unordered map**: *insert*: n/2 random numbers, n/2 sequential numbers. *erase*: n/2 keys in the map, n/2 random keys.
@@ -117,8 +117,8 @@ Benchmark notes:
## Naming conventions
- Container names are prefixed by `c`, e.g. `cvec`, `cstr`.
-- Public STC macros are prefixed by `c_`, e.g. `c_foreach`, `c_make`.
-- Template parameter macros are prefixed by `i_`, e.g. `i_val`, `i_type`.
+- Public STC macros are prefixed by `c_`, e.g. `c_foreach`, `c_init`.
+- Template parameter macros are prefixed by `i_`, e.g. `i_key`, `i_type`.
- All containers can be initialized with `{0}`, i.e. no heap allocation used by default init.
- Common types for a container type Con:
- Con
@@ -147,10 +147,10 @@ Benchmark notes:
STC containers have similar functionality to C++ STL standard containers. All containers except for a few,
like **cstr** and **cbits** are generic/templated. No type casting is used, so containers are type-safe like
templated types in C++. However, to specify template parameters with STC, you define them as macros prior to
-including the container:
+including the container.
```c
-#define i_type Floats // Container type name; unless defined name would be cvec_float
-#define i_val float // Container element type
+#define i_type Floats // Container type name (optional); if not defined name would be cvec_float
+#define i_key float // Container element type
#include <stc/cvec.h> // "instantiate" the desired container type
#include <stdio.h>
@@ -164,39 +164,44 @@ int main(void)
for (int i = 0; i < Floats_size(&nums); ++i)
printf(" %g", nums.data[i]);
- Floats_sort(&nums);
-
c_foreach (i, Floats, nums) // Alternative and recommended way to iterate.
printf(" %g", *i.ref); // i.ref is a pointer to the current element.
Floats_drop(&nums); // cleanup memory
}
```
-You may switch to a different container type, e.g. a sorted set (csset):
+Note that `i_val*` template parameters can be used instead of `i_key*` for *non-map* containers.
+
+Switching to a different container type, e.g. a sorted set (csset):
[ [Run this code](https://godbolt.org/z/qznfa65e1) ]
```c
#define i_type Floats
-#define i_val float
+#define i_key float
#include <stc/csset.h> // Use a sorted set instead
#include <stdio.h>
-int main()
+int main(void)
{
Floats nums = {0};
Floats_push(&nums, 30.f);
Floats_push(&nums, 10.f);
Floats_push(&nums, 20.f);
- // already sorted, print the numbers
+ // print the numbers (sorted)
c_foreach (i, Floats, nums)
printf(" %g", *i.ref);
Floats_drop(&nums);
}
```
-For user-defined struct elements, `i_cmp` compare function should be defined as the default `<` and `==`
-only works for integral types. *Alternatively, `#define i_opt c_no_cmp` to disable sorting and searching*. Similarily, if an element destructor `i_valdrop` is defined, `i_valclone` function is required.
+Comparison/lookup functions are enabled by default for associative containers and priority queue (cmap, cset, csmap, csset, cpque). To enable it for the remaining containers, define `i_cmp` or `i_less` (and optionally `i_eq`) on the element type. If the element is an integral type, simply define `i_use_cmp` to use `<` and `==` operators for comparisons.
+
+Note that for `#define i_keyclass Type`, defining `i_use_cmp` means that *Type_cmp()* function is expected to exist (along with *Type_clone()* and *Type_drop()*).
+
+To summarize, `i_use_cmp` is only needed to enable comparison (sort/search) functions when defining cstack, cvec, cqueue, cdeq, carc, cbox. With built-in types, it enables the comparison operators, whereas for keyclass types, it binds comparison to its Type_cmp() function.
+
+If an element destructor `i_keydrop` is defined, `i_keyclone` function is required.
*Alternatively `#define i_opt c_no_clone` to disable container cloning.*
Let's make a vector of vectors, which can be cloned. All of its element vectors will be destroyed when destroying the Vec2D.
@@ -206,12 +211,11 @@ Let's make a vector of vectors, which can be cloned. All of its element vectors
#include <stdio.h>
#define i_type Vec
-#define i_val float
+#define i_key float
#include <stc/cvec.h>
#define i_type Vec2D
-#define i_valclass Vec // Use i_valclass when element type has "members" _clone(), _drop() and _cmp().
-#define i_opt c_no_cmp // Disable cmp (search/sort) for Vec2D because Vec_cmp() is not defined.
+#define i_keyclass Vec // Use i_keyclass instead i_key when element type has "members" _clone(), _drop() and _cmp().
#include <stc/cvec.h>
int main(void)
@@ -237,21 +241,22 @@ int main(void)
```
This example uses four different container types:
-[ [Run this code](https://godbolt.org/z/x5YKeMrEh) ]
+[ [Run this code](https://godbolt.org/z/j68od14hv) ]
```c
#include <stdio.h>
#define i_key int
-#include <stc/cset.h> // cset_int: unordered set
+#include <stc/cset.h> // cset_int: unordered set (assume i_key is basic type, uses `==` operator)
struct Point { float x, y; };
// Define cvec_pnt with a less-comparison function for Point.
-#define i_val struct Point
-#define i_less(a, b) a->x < b->x || (a->x == b->x && a->y < b->y)
+#define i_key struct Point
+#define i_less(a, b) a->x < b->x || (a->x == b->x && a->y < b->y) // enable sort/search
#define i_tag pnt
#include <stc/cvec.h> // cvec_pnt: vector of struct Point
-#define i_val int
+#define i_key int
+#define i_use_cmp // enable sort/search. Use native `<` and `==` operators
#include <stc/clist.h> // clist_int: singly linked list
#define i_key int
@@ -333,49 +338,29 @@ After erasing the elements found:
---
## Installation
-Because it is headers-only, headers can simply be included in your program. By default, functions are static
-(some inlined). You may add the *include* folder to the **CPATH** environment variable to
-let GCC, Clang, and TinyC locate the headers.
+STC is primarily a "headers-only" library, so most headers can simply be included in your program. By default,
+all "templated" functions are static (many inlined). If you add the STC *include* folder to the **CPATH**
+environment variable, GCC, Clang, and TinyC will locate the headers automatically.
-If containers are used across several translation units with common instantiated container types, it is
-recommended to build as a "library" with external linking to minimize executable size. To enable this,
-specify `-DSTC_HEADER` as compiler option in your build environment. Next, place all the instantiations
-of the containers used inside a single C-source file as in the example below, and `#define STC_IMPLEMENT` at top.
-You may also cherry-pick shared linking mode on individual containers by `#define i_header` and
-`#define i_implement`, or force static symbols by `#define i_static` before container includes.
-
-As a special case, there may be non-templated functions in templated containers that should be implemented only
-once and if needed. Currently, define `i_extern` before including **clist** for its sorting function, and before
-**cregex** or **utf8** to implement them (global `STC_EXTERN` can alternatively be defined).
-
-It is possible to generate single headers by executing the python script `src/singleheader.py header-file > single`.
-
-Conveniently, `src\libstc.c` implements non-templated functions as shared symbols for **cstr**, **csview**,
-**cbits** and **crand**. When building in shared mode (-DSTC_HEADER), you may include this file in your project,
-or define your own as descibed above.
+The templated container functions are defined with static linking by default, which is normally optimal
+for both performance and compiled binary size. However, some common container type instances, e.g. `cvec_int`
+may be used in several translation units. When they are used in more than 3-4, consider creating a separate
+header file for them [as described here](#1-include-as-a-header-file). Now it will use shared
+linking, so *one* c-file must implement the templated container, e.g.:
```c
-// stc_libs.c
-#define STC_IMPLEMENT
-
-#include <stc/cstr.h>
-#include "Point.h"
-
-#define i_key int
-#define i_val int
-#define i_tag ii
-#include <stc/cmap.h> // cmap_ii: int => int
+#define i_implement
+#include "cvec_int.h"
+```
+The non-templated string type **cstr** uses shared linking by default, but can have static linking instead by
+`#define i_static`. Same for the string-view type **csview**, but most of its functions are static inlined, so
+linking specifications and implementation are only needed for a few lesser used functions.
-#define i_key int64_t
-#define i_tag ix
-#include <stc/cset.h> // cset_ix
+Conveniently, `src\libstc.c` implements all the non-templated functions with shared linking for **cstr**,
+**csview**, **cregex**, **utf8**, and **crand**.
-#define i_val int
-#include <stc/cvec.h> // cvec_int
+As a special case, you can `#define i_import` before including **cregex** or **cstr** to implement the dependent
+**utf8** functions (proper utf8 case conversions, etc.). Or link with src\libstc.
-#define i_val Point
-#define i_tag pnt
-#include <stc/clist.h> // clist_pnt
-```
---
## Specifying template parameters
@@ -383,16 +368,16 @@ Each templated type requires one `#include`, even if it's the same container bas
The template parameters are given by a `#define i_xxxx` statement, where *xxxx* is the parameter name.
The list of template parameters:
-- `i_key` *Type* - Element key type for map/set only. **[required]**.
-- `i_val` *Type* - Element value type. **[required for]** cmap/csmap, it is the mapped value type.
-- `i_cmp` *Func* - Three-way comparison of two *i_keyraw*\* or *i_valraw*\* - **[required for]** non-integral *i_keyraw* elements unless *i_opt* is defined with *c_no_cmp*.
+- `i_key` *Type* - Element key type. **[required]**. Note: `i_val` *may* be used instead for non-maps (not recommended).
+- `i_val` *Type* - Element value type. **[required for]** cmap/csmap as the mapped value type.
+- `i_cmp` *Func* - Three-way comparison of two *i_keyraw*\* or *i_valraw*\* - **[required for]** non-integral *i_keyraw* elements.
- `i_hash` *Func* - Hash function taking *i_keyraw*\* - defaults to *c_default_hash*. **[required for]** ***cmap/cset*** with non-POD *i_keyraw* elements.
- `i_eq` *Func* - Equality comparison of two *i_keyraw*\* - defaults to *!i_cmp*. Companion with *i_hash*.
Properties:
- `i_tag` *Name* - Container type name tag. Defaults to *i_key* name.
- `i_type` *Name* - Full container type name. Alternative to *i_tag*.
-- `i_opt` *Flags* - Boolean properties: may combine *c_no_cmp*, *c_no_clone*, *c_no_atomic*, *c_is_forward*, *c_static*, *c_header* with the *|* separator.
+- `i_opt` *Flags* - Boolean properties: may combine *c_no_clone*, *c_no_atomic*, *c_is_forward*, *c_static*, *c_header* with the *|* separator.
Key:
- `i_keydrop` *Func* - Destroy map/set key func - defaults to empty destructor.
@@ -413,7 +398,7 @@ Specials: Meta-template parameters. Use instead of `i_key` / `i_val`.
If `i_keyraw` is defined, it sets `i_keyto` = *Type_toraw()* and `i_keyfrom` = *Type_from()*.
Only functions required by the container type is required to be defined. E.g.:
- *Type_hash()* and *Type_eq()* are only required by **cmap**, **cset** and smart pointers.
- - *Type_cmp()* is not used by **cstack** and **cmap/cset**, or if *#define i_opt c_no_cmp* is specified.
+ - *Type_cmp()* is not used by **cstack** and **cmap/cset**.
- *Type_clone()* is not used if *#define i_opt c_no_clone* is specified.
- `i_key_str` - Sets `i_keyclass` = *cstr*, `i_tag` = *str*, and `i_keyraw` = *const char*\*. Defines both type convertion
`i_keyfrom`, `i_keyto`, and sets `i_cmp`, `i_eq`, `i_hash` functions with *const char\*\** as argument.
@@ -424,7 +409,6 @@ NB: Do not use when defining carc/cbox types themselves.
- `i_valclass` *Type*, `i_val_str`, `i_val_ssv`, `i_valboxed` - Similar rules as for ***key***.
**Notes**:
-- Instead of defining `i_cmp`, you may define *i_opt c_no_cmp* to disable *searching and sorting* functions.
- Instead of defining `i_*clone`, you may define *i_opt c_no_clone* to disable *clone* functionality.
- For `i_keyclass`, if *i_keyraw* is defined along with it, *i_keyfrom* may also be defined to enable the *emplace*-functions. NB: the signature for ***cmp***, ***eq***, and ***hash*** uses *i_keyraw* as input.
@@ -458,7 +442,7 @@ and non-emplace methods:
#define i_implement // define in ONE file to implement longer functions in cstr
#include <stc/cstr.h>
-#define i_val_str // special macro to enable container of cstr
+#define i_key_str // special macro to enable container of cstr
#include <stc/cvec.h> // vector of string (cstr)
...
cvec_str vec = {0};
@@ -518,36 +502,93 @@ last example on the **cmap** page demonstrates how to specify a map with non-tri
Define `i_type` instead of `i_tag`:
```c
#define i_type MyVec
-#define i_val int
+#define i_key int
#include <stc/cvec.h>
-myvec vec = MyVec_init();
-MyVec_push_back(&vec, 1);
+MyVec vec = {0};
+MyVec_push(&vec, 42);
...
```
---
## Forward declarations
-It is possible to forward declare containers. This is useful when a container is part of a struct,
-but still not expose or include the full implementation / API of the container.
+There are two ways to pre-declare templated containers in header files:
+
+1. Include the templated container type instance as a header file. This also exposes all container
+functions, which can be used by client code. It requires that the element type is complete.
+2. Or, pre-declare the container type only. In this case, the container can be a "private" member of a
+user struct (the container functions will not be available to the user).
+
+### 1. Include as a header file
+
+Create a dedicated header for the container type instance:
+```c
+#ifndef PointVec_H_
+#define PointVec_H_
+// Do not to include user defined headers here if they use templated containers themselves
+
+#define i_type PointVec
+#define i_val struct Point // NB! Element type must be complete at this point!
+#define i_header // Do not implement, only expose API
+#include <stc/cvec.h>
+
+#endif
+```
+Usage from e.g. other headers is trivial:
```c
-// Header file
-#include <stc/forward.h> // only include data structures
-forward_cstack(cstack_pnt, struct Point); // declare cstack_pnt (and cstack_pnt_value, cstack_pnt_iter);
- // struct Point may be an incomplete type.
+#ifndef Dataset_H_
+#define Dataset_H_
+#include "Point.h" // include element type separately
+#include "PointVec.h"
+
typedef struct Dataset {
- cstack_pnt vertices;
- cstack_pnt colors;
+ PointVec vertices;
+ PointVec colors;
} Dataset;
+...
+#endif
+```
-// Implementation
-#define i_is_forward // flag that the container was forward declared.
-#define i_val struct Point
-#define i_tag pnt
-#include <stc/cstack.h>
+Implement PointVec in a c-file:
+```c
+#include "Point.h"
+#define i_implement // define immediately before PointVec.h
+#include "PointVec.h"
+...
```
+### 2. Forward declare only
+```c
+// Dataset.h
+#ifndef Dataset_H_
+#define Dataset_H_
+#include <stc/forward.h> // include various container data structure templates
+
+// declare PointVec. Note: struct Point may be an incomplete/undeclared type.
+forward_cvec(PointVec, struct Point);
+
+typedef struct Dataset {
+ PointVec vertices;
+ PointVec colors;
+} Dataset;
+
+void Dataset_drop(Dataset* self);
+...
+#endif
+```
+Define and use the "private" container in the c-file:
+```c
+// Dataset.c
+#include "Dataset.h"
+#include "Point.h" // Point must be defined here.
+
+#define i_is_forward // flag that the container was forward declared.
+#define i_type PointVec
+#define i_val struct Point
+#include <stc/cvec.h> // Implements PointVec with static linking by default
+...
+```
---
## Per container-instance customization
Sometimes it is useful to extend a container type to store extra data, e.g. a comparison
@@ -564,8 +605,8 @@ It adds a MemoryContext to each container by defining the `i_extend` template pa
the by inclusion of `<stc/extend.h>`.
```c
// stcpgs.h
-#define pgs_malloc(sz) MemoryContextAlloc(c_getcon(self)->memctx, sz)
-#define pgs_calloc(n, sz) MemoryContextAllocZero(c_getcon(self)->memctx, (n)*(sz))
+#define pgs_malloc(sz) MemoryContextAlloc(c_extend(self)->memctx, sz)
+#define pgs_calloc(n, sz) MemoryContextAllocZero(c_extend(self)->memctx, (n)*(sz))
#define pgs_realloc(p, sz) (p ? repalloc(p, sz) : pgs_malloc(sz))
#define pgs_free(p) (p ? pfree(p) : (void)0) // pfree/repalloc does not accept NULL.
@@ -574,12 +615,12 @@ the by inclusion of `<stc/extend.h>`.
#define i_extend MemoryContext memctx;
#include <stc/extend.h>
```
-To use it, define both `i_type` and `i_con` (the container type) before including the custom header:
+To use it, define both `i_type` and `i_base` (the container type) before including the custom header:
```c
#define i_type IMap
+#define i_base csmap
#define i_key int
#define i_val int
-#define i_con csmap
#include "stcpgs.h"
// Note the wrapper struct type is IMap_ext. IMap is accessed by .get
@@ -611,6 +652,29 @@ STC is generally very memory efficient. Memory usage for the different container
---
# Version History
+
+## Version 4.3
+- Breaking changes:
+ - **cstr** and **csview** now uses *shared linking* by default. Implement by either defining `i_implement` or `i_static` before including.
+ - Renamed <stc/calgo.h> => `<stc/algorithm.h>`
+ - Moved <stc/algo/coroutine.h> => `<stc/coroutine.h>`
+ - Much improved with some new API and added features.
+ - Removed deprecated <stc/crandom.h>. Use `<stc/crand.h>` with the new API.
+ - Reverted names _unif and _norm back to `_uniform` and `_normal`.
+ - Removed default comparison for **clist**, **cvec** and **cdeq**:
+ - Define `i_use_cmp` to enable comparison for built-in i_key types (<, ==).
+ - Use of `i_keyclass` still expects comparison functions to be defined.
+ - Use of `i_keyboxed` compares stored pointers instead of pointed to values if comparison not defined.
+ - Renamed input enum flags for ***cregex***-functions.
+- **cspan**: Added **column-major** order (fortran) multidimensional spans and transposed views (changed representation of strides).
+- All new faster and smaller **cqueue** and **cdeq** implementations, using a circular buffer.
+- Renamed i_extern => `i_import` (i_extern deprecated).
+ - Define `i_import` before `#include <stc/cstr.h>` will also define full utf8 case conversions.
+ - Define `i_import` before `#include <stc/cregex.h>` will also define cstr + utf8 tables.
+- Renamed c_make() => ***c_init()*** macro for initializing containers with element lists. c_make deprecated.
+- Removed deprecated uppercase flow-control macro names.
+- Other smaller additions, bug fixes and improved documentation.
+
## Version 4.2
- New home! And online single headers for https://godbolt.org
- Library: https://github.com/stclib/STC
@@ -620,7 +684,6 @@ STC is generally very memory efficient. Memory usage for the different container
- Added new crand.h API & header. Old crandom.h is deprecated.
- Added `c_const_cast()` typesafe macro.
- Removed RAII macros usage from examples
-- Renamed c_foreach_r => `c_foreach_rv`
- Renamed c_flt_count(i) => `c_flt_counter(i)`
- Renamed c_flt_last(i) => `c_flt_getcount(i)`
- Renamed c_ARRAYLEN() => c_arraylen()
@@ -634,9 +697,9 @@ Major changes:
- Customizable allocator [per templated container type](https://github.com/tylov/STC/discussions/44#discussioncomment-4891925).
- Updates on **cregex** with several [new unicode character classes](docs/cregex_api.md#regex-cheatsheet).
- Algorithms:
- - [crange](docs/ccommon_api.md#crange) - similar to [boost::irange](https://www.boost.org/doc/libs/release/libs/range/doc/html/range/reference/ranges/irange.html) integer range generator.
- - [c_forfilter](docs/ccommon_api.md#c_forfilter) - ranges-like view filtering.
- - [csort](include/stc/algo/csort.h) - [fast quicksort](misc/benchmarks/various/csort_bench.c) with custom inline comparison.
+ - [crange](docs/algorithm_api.md#crange) - similar to [boost::irange](https://www.boost.org/doc/libs/release/libs/range/doc/html/range/reference/ranges/irange.html) integer range generator.
+ - [c_forfilter](docs/algorithm_api.md#c_forfilter) - ranges-like view filtering.
+ - [csort](include/stc/algo/sort.h) - [fast quicksort](misc/benchmarks/various/csort_bench.c) with custom inline comparison.
- Renamed `c_ARGSV()` => `c_SV()`: **csview** print arg. Note `c_sv()` is shorthand for *csview_from()*.
- Support for [uppercase flow-control](include/stc/priv/altnames.h) macro names in ccommon.h.
- Some API changes in **cregex** and **cstr**.
@@ -696,10 +759,10 @@ Major changes:
- Renamed: *csptr_X_make()* to `carc_X_from()`.
- Renamed: *cstr_new()* to `cstr_lit(literal)`, and *cstr_assign_fmt()* to `cstr_printf()`.
- Renamed: *c_default_fromraw()* to `c_default_from()`.
-- Changed: the [**c_apply**](docs/ccommon_api.md) macros API.
+- Changed: the [**c_apply**](docs/algorithm_api.md) macros API.
- Replaced: *csview_first_token()* and *csview_next_token()* with one function: `csview_token()`.
- Added: **checkauto** tool for checking that c-source files uses `c_auto*` macros correctly.
- Added: general `i_keyclass` / `i_valclass` template parameters which auto-binds template functions.
-- Added: `i_opt` template parameter: compile-time options: `c_no_cmp`, `c_no_clone`, `c_no_atomic`, `c_is_forward`; may be combined with `|`
+- Added: `i_opt` template parameter: compile-time options: `c_no_clone`, `c_no_atomic`, `c_is_forward`; may be combined with `|`
- Added: [**cbox**](docs/cbox_api.md) type: smart pointer, similar to [Rust Box](https://doc.rust-lang.org/rust-by-example/std/box.html) and [std::unique_ptr](https://en.cppreference.com/w/cpp/memory/unique_ptr).
-- Added: [**c_forpair**](docs/ccommon_api.md) macro: for-loop with "structured binding"
+- Added: [**c_forpair**](docs/algorithm_api.md) macro: for-loop with "structured binding"