hare

The Hare programming language
git clone https://git.torresjrjr.com/hare.git
Log | Files | Refs | README | LICENSE

commit 3628b8ab8ce153d7189a27f5d66860552e9a38b4
parent 045132350572ad8f273c580685218821c7dd562e
Author: Sebastian <sebastian@sebsite.pw>
Date:   Sun, 20 Mar 2022 00:28:32 -0400

slice: add more void functions

Signed-off-by: Sebastian <sebastian@sebsite.pw>

Diffstat:
Mslice/void.ha | 64++++++++++++++++++++++++++++++++++++++++++++++++++++++++--------
1 file changed, 56 insertions(+), 8 deletions(-)

diff --git a/slice/void.ha b/slice/void.ha @@ -3,26 +3,74 @@ use rt; use types; -// Appends an item, or items, to a slice, returning a new slice. +// Appends an item, or multiple items, to a slice. export fn appendto(sl: *[]void, itemsz: size, items: const *void...) void = { + const repr = sl: *types::slice; + insertinto(sl, itemsz, repr.length, items...); +}; + +@test fn appendto() void = { + let input: []int = []; + let num = 1337; + appendto(&input: *[]void, size(int), &num, &num); + assert(len(input) == 2 && input[0] == 1337 && input[1] == 1337); + num = 7331; + appendto(&input: *[]void, size(int), &num); + assert(len(input) == 3 && input[0] == 1337 && input[1] == 1337 + && input[2] == 7331); + free(input); +}; + +// Inserts an item, or multiple items, to a slice, in O(n) time. +export fn insertinto( + sl: *[]void, + itemsz: size, + idx: size, + items: const *void... +) void = { if (len(items) == 0) { return; }; let sl = sl: *types::slice; - let end = sl.length; sl.length += len(items); rt::ensure(sl, itemsz); let data = sl.data: *[*]u8; + rt::memmove(&data[(idx + len(items)) * itemsz], &data[idx * itemsz], + (sl.length - len(items) - idx) * itemsz); for (let i = 0z; i < len(items); i += 1) { - rt::memcpy(&data[(end + i) * itemsz], items[i], itemsz); + rt::memcpy(&data[(idx + i) * itemsz], items[i], itemsz); }; }; -@test fn appendto() void = { - let input: []int = []; - let num = 1337; - appendto(&input: *[]void, size(int), &num, &num); - assert(len(input) == 2 && input[0] == 1337 && input[1] == 1337); +@test fn insertinto() void = { + let input: []int = alloc([1, 3], 2); + let num = 2; + insertinto(&input: *[]void, size(int), 1, &num, &num); + assert(len(input) == 4 && input[0] == 1 && input[1] == 2 + && input[2] == 2 && input[3] == 3); + free(input); +}; + +// Deletes a range of items from a slice, in O(n) time, without freeing memory. +export fn deletefrom(sl: *[]void, itemsz: size, start: size, end: size) void = { + assert(start <= end); + if (start == end) { + return; + }; + let sl = sl: *types::slice; + let data = sl.data: *[*]u8; + rt::memmove(&data[start * itemsz], &data[end * itemsz], + (sl.length - start) * itemsz); + sl.length -= end - start; +}; + +@test fn deletefrom() void = { + let input: []int = alloc([1, 2, 3, 4, 5], 5); + deletefrom(&input: *[]void, size(int), 1, 1); + assert(len(input) == 5); + deletefrom(&input: *[]void, size(int), 1, 3); + assert(len(input) == 3 && input[0] == 1 && input[1] == 4 + && input[2] == 5); free(input); };