summaryrefslogtreecommitdiff
path: root/box/list.tnsl
diff options
context:
space:
mode:
Diffstat (limited to 'box/list.tnsl')
-rw-r--r--box/list.tnsl149
1 files changed, 149 insertions, 0 deletions
diff --git a/box/list.tnsl b/box/list.tnsl
new file mode 100644
index 0000000..58278e4
--- /dev/null
+++ b/box/list.tnsl
@@ -0,0 +1,149 @@
+
+# List type - array backed list of elements
+struct List {
+ ~void data,
+
+ uint
+ count,
+ size,
+ _elsz
+}
+
+uint VECTOR_MIN_ELEMENTS = 4
+uint VECTOR_MAX_GROW = 256
+
+/; method Vector
+
+ /; init (uint elsz)
+ self._elsz = elsz
+ self.size = VECTOR_MIN_ELEMENTS
+ self.count = 0
+ self.data = _alloc(self.size * self._elsz)
+ ;/
+
+ /; from_cstr(~uint8 cstr)
+ self.init(1)
+ self.push_cstr(cstr)
+ ;/
+
+ /; _grow (uint i)
+ self.size = self.size + i
+ self.data = _realloc(self.data, self.size * self._elsz)
+ ;/
+
+ /; get (uint index) [~void]
+ /; if (index !< self.count)
+ return NULL
+ ;/
+
+ return self.data + index * self._elsz
+ ;/
+
+ /; push (~void el)
+ /; if (self.size == self.count + 1)
+ /; if (self.size < VECTOR_MAX_GROW)
+ self._grow(self.size)
+ ;; else
+ self._grow(VECTOR_MAX_GROW)
+ ;/
+ ;/
+
+ ~void start = self.data + self.count * self._elsz
+ /; loop (int i = 0; i < self._elsz) [i++]
+ ~uint8 to = start + i
+ ~uint8 from = el + i
+ to` = from`
+ ;/
+ self.count++
+ ;/
+
+ /; replace (int index, ~void el)
+ ~uint8 start = self.get(index)
+ /; if (start == NULL)
+ return
+ ;/
+
+ /; loop (int i = 0; i < self._elsz) [i++]
+ ~uint8 to = start + i
+ ~uint8 from = el + i
+ to` = from`
+ ;/
+ ;/
+
+ /; _shrink(uint i)
+ /; if (i !< self.size)
+ self.size = 1
+ ;; else
+ self.size = self.size - i
+ ;/
+
+ self.data = _realloc(self.data, self.size * self._elsz)
+ ;/
+
+ /; pop
+ self.remove(self.count - 1)
+ ;/
+
+ /; remove (int index)
+ /; if (index < 0 || index !< self.count)
+ return
+ ;/
+
+ /; if (self.count > 1)
+ /; loop (int i = index * self._elsz; i < (self.count - 1) * self._elsz) [i++]
+ ~uint8 to = self.data + i
+ ~uint8 from = self.data + i + self._elsz
+ to` = from`
+ ;/
+ ;/
+
+ self.count--
+
+ /; if (self.count < self.size / 2)
+ self._shrink(self.size / 3)
+ ;/
+ ;/
+
+ /; push_char (uint8 ch)
+ self.push(~ch)
+ ;/
+
+ /; push_cstr(~uint8 ch)
+ /; loop (ch` !== 0) [ch++]
+ self.push(ch)
+ ;/
+ ;/
+
+ /; as_cstr [~uint8]
+ ~uint8 z = self.data + self.count
+ z` = 0
+ return self.data
+ ;/
+
+ /; end
+ self.count = 0
+ self.size = 0
+ self._elsz = 0
+ _delete(self.data)
+ ;/
+
+ /; copy [Vector]
+ Vector out
+
+ out.init(self._elsz)
+ /; loop (int i = 0; i < self.count) [i++]
+ ~int tmp = self.get(i)
+ out.push(tmp)
+ ;/
+
+ return out
+ ;/
+
+ /; back [~void]
+ /; if (self.count > 0)
+ return self.get(self.count - 1)
+ ;/
+ return NULL
+ ;/
+;/
+