diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..b4fd014 --- /dev/null +++ b/.gitignore @@ -0,0 +1,4 @@ +*.o +*.exe +test.c +test \ No newline at end of file diff --git a/.vscode/launch.json b/.vscode/launch.json new file mode 100644 index 0000000..a35e3f5 --- /dev/null +++ b/.vscode/launch.json @@ -0,0 +1,29 @@ +{ + // 使用 IntelliSense 了解相关属性。 + // 悬停以查看现有属性的描述。 + // 欲了解更多信息,请访问: https://go.microsoft.com/fwlink/?linkid=830387 + "version": "0.2.0", + "configurations": [ + { + "name": "gcc - 生成和调试活动文件", + "type": "cppdbg", + "request": "launch", + "program": "${fileDirname}/${fileBasenameNoExtension}", + "args": [], + "stopAtEntry": false, + "cwd": "${workspaceFolder}", + "environment": [], + "externalConsole": false, + "MIMode": "gdb", + "setupCommands": [ + { + "description": "为 gdb 启用整齐打印", + "text": "-enable-pretty-printing", + "ignoreFailures": true + } + ], + "preLaunchTask": "gcc build active file", + "miDebuggerPath": "/usr/bin/gdb" + } + ] +} \ No newline at end of file diff --git a/.vscode/settings.json b/.vscode/settings.json new file mode 100644 index 0000000..337ed14 --- /dev/null +++ b/.vscode/settings.json @@ -0,0 +1,6 @@ +{ + "files.associations": { + "pile_vector.h": "c", + "pile_class.h": "c" + } +} \ No newline at end of file diff --git a/.vscode/tasks.json b/.vscode/tasks.json new file mode 100644 index 0000000..4a36ee9 --- /dev/null +++ b/.vscode/tasks.json @@ -0,0 +1,19 @@ +{ + "tasks": [ + { + "type": "shell", + "label": "gcc build active file", + "command": "/usr/bin/gcc", + "args": [ + "-g", + "${file}", + "-o", + "${fileDirname}/${fileBasenameNoExtension}" + ], + "options": { + "cwd": "/usr/bin" + } + } + ], + "version": "2.0.0" +} \ No newline at end of file diff --git a/README.md b/README.md new file mode 100644 index 0000000..d4e8ac7 --- /dev/null +++ b/README.md @@ -0,0 +1,231 @@ +# Pile + +Pile aims to build an elegant library and scripting language for small devices. + +It has several components including pile class, pile library, pile runtime and pile intepreter. + +## Pile Class + +Pile uses C macro and struct to implement classes. + +Here's an example: + +```c +// test_class.h +#include "pile_class.h" +#include "pile_types.h" +#define PILE_CLASS_SHORTCUTS true +class(test_class) +{ + pile_int_t a; + + pile_int_t def_fn(test_class, get_a); + def_destruct(test_class); +}; + +// test_class.c +pile_int_t impl_fn(test_class, get_a) +{ + return self->a; +} +impl_construct(test_class, pile_int_t a) +{ + self->a = a; + _assgin(test_class, get_a); +} +impl_default_destruct(test_class); + +// main.c +#include +#include "test_class.h" + +int main() { + new(test_class, ins, 10); + printf("%d\r\n", ins->get_a(ins)); + ins->a = 1000; + printf("%d\r\n", call(ins, get_a)); + del(ins); + renew(test_class, ins, 200); + printf("%d\r\n", ins->get_a(ins)); + del(ins); + return 0; +} +``` + +### Class Shortcuts + +The macros have shortcuts when `PILE_CLASS_SHORTCUTS` is defined. + +You can disable that if the shortcuts cause name conflicts. + +| Shortcut | Origin | +| ----------------------- | ------------------------------- | +| `class` | `PILE_CLASS` | +| `new` | `PILE_NEW` | +| `del` | `PILE_DEL` | +| `impl_fn` | `PILE_CLASS_METHOD` | +| `impl_construct` | `PILE_CLASS_CONSTRUCTOR` | +| `impl_destruct` | `PILE_CLASS_DESTRUCTOR` | +| `impl_default_destruct` | `PILE_CLASS_DESTRUCTOR_DEFAULT` | +| `_assign` | `PILE_ASSIGN_METHOD` | +| `def_fn` | `PILE_DEFINE_METHOD` | +| `def_destruct` | `PILE_DEFINE_DESTRUCT` | +| `call` | `PILE_CALL` | + +In the document, we will use shortcuts to tell. + +### Define a class + +```c +class(test_class) +{ + pile_int_t a; + + void def_fn(test_class, set_a, pile_int_t a); + + def_destruct(test_class); +}; +``` + +In the code above, we define a class named `test_class`. + +To define a class, we need to use macro `class` or `PILE_CLASS`. It receives an argument as the class name. Then a struct body need to be followed. + +> Note: after the brackets the semicolon(`;`) cannot be missed. + +Because of the limits of C language, pile doesn't support private atrributes. The properties can be defined in normal struct way, like: `pile_str_t str;`. + +When defining class methods, we use `def_fn` or `PILE_DEFINE_METHOD` macros. The macro receives its first parameter as the class name, and the second as method name. The return type should be defined before calling the macro, and the parameter list should start at the third macro parameter, separated by commas. + +Note the constructor should **not** be defined in the class definition. But the destructor must be defined using `def_destruct` or `PILE_DEFINE_DESTRUCT` macro. The macro receives its first parameter as the class name and no other parameters should be followed. + +The following types will be defined as in the example: + +- struct test_class: The original struct type +- test_class_t: Orignal type defined using typedef +- test_class_ptr_t: Pointer to the original type (instance type) + +### Implement a method + +> Note: constructors and destructors should be defined using another macro, which will be described in the next section. + +When implementing a method, macro `impl_fn` or `PILE_CLASS_METHOD` should be used. + +```c +void impl_fn(test_class, set_a, pile_int_t a) +{ + self->a = a; +} +``` + +The return type should be defined before calling the macro. + +The first parameter is the class name while the second is the method name. + +The following parameters are argument list of the method. + +Inside the function body we can use `self` to access the instance. + +### Implementing a destructor + +In a destructor, a class can free the resources it uses. + +Use `impl_destruct` or `PILE_CLASS_DESTRUCTOR` to implement one. + +Example: + +```c +impl_destruct(test_class) +{ + PILE_FREE(self->data); +} +``` + +When a class does nothing in a destructor, you can use `impl_default_destruct`. + +Example: + +```c +impl_default_destruct(test_class); +``` + +### Implement a constructor + +A constructor need to do two things: + +1. Init the properties +2. Assign methods + +You can use `impl_construct` or `PILE_CLASS_CONSTRUCT` macros to implement. + +The first parameter is class name, and it can receive a parameter list. + +```c +impl_construct(test_class, pile_int_t a) +{ + _assign(test_class, set_a); + + self->set_a(a); +} +``` + +The `_assign` or `PILE_ASSIGN` macro can automatically assign a method to a class. + +All the methods need to be assigned in the constructor, + +The macro receives two parameters, where the first one is the class name and the second one is the method name. + +### Creating a new instance + +You can use `new` or `PILE_NEW` macros to create a new instance. + +Example: + +```c +new(test_class, ins, 123); +``` + +The first parameter is the class name, while the second is the variable name. The following parameters will be passed to the constructor. Then you can use `ins` to access the instance. + +The above code will create a new variable with type `test_class_ptr_t`. + +If you have a variable typed that already available, you can use `renew` or `PILE_RENEW` macro to re-initialize it. + +Example: + +```c +test_class_ptr_t ins; +renew(test_class, ins, 123); +``` + +### Deleting a instance + +Use `del` or `PILE_DEL` macros. + +Example: + +```c +del(ins); +``` + +The parameter is the variable name of the instance. + +### Calling a method + +You can use `ins->method_name(ins, 123);` to call a method. + +Note the first parameter should pass the variable again. + +If you use `call` or `PILE_CALL` macro, then you don't need to pass itself again. It looks like: + +```c +call(test_cass, set_a, 100); +``` + +The first parameter is the class name, while the second one is the method name. + +## Shortcuts + +pcert = pile_container_t + +pvcoer = PILE_VALUE_CONTAINER diff --git a/pile_class.h b/pile_class.h new file mode 100644 index 0000000..bdb1dc7 --- /dev/null +++ b/pile_class.h @@ -0,0 +1,87 @@ +#ifndef _PILE_CLASS_H_ +#define _PILE_CLASS_H_ true + +#ifdef __cplusplus +extern "C" +{ +#endif + +#include "pile_memory.h" +#pragma GCC diagnostic ignored "-Wincompatible-pointer-types" + +#define PILE_CLASS(CLASS_NAME) \ + typedef struct CLASS_NAME CLASS_NAME##_t; \ + typedef CLASS_NAME##_t *CLASS_NAME##_ptr_t; \ + struct CLASS_NAME + +#define PILE_RENEW(CLASS_NAME, VARIABLE_NAME, args...) \ + VARIABLE_NAME = \ + (CLASS_NAME##_ptr_t)PILE_MALLOC(sizeof(CLASS_NAME##_t)); \ + VARIABLE_NAME->destruct = _class_##CLASS_NAME##_destruct; \ + _class_##CLASS_NAME##_construct(VARIABLE_NAME, ##args) + +#define PILE_NEW(CLASS_NAME, VARIABLE_NAME, args...) \ + CLASS_NAME##_ptr_t VARIABLE_NAME; \ + PILE_RENEW(CLASS_NAME, VARIABLE_NAME, ##args) + +#define PILE_NEW_INDIRECT(CLASS_NAME, VARIABLE_NAME, args...) \ + CLASS_NAME##_t VARIABLE_NAME##_prototype; \ + CLASS_NAME##_ptr_t VARIABLE_NAME = \ + &VARIABLE_NAME##_prototype; \ + _class_##CLASS_NAME##_construct(VARIABLE_NAME, ##args) + +#define PILE_DEL(VARIABLE_NAME) \ + VARIABLE_NAME->destruct(VARIABLE_NAME); \ + PILE_FREE(VARIABLE_NAME) + +#define PILE_CLASS_CONSTRUCTOR(CLASS_NAME, args...) \ + void _class_##CLASS_NAME##_construct( \ + CLASS_NAME##_ptr_t self, ##args) + +#define PILE_CLASS_METHOD(CLASS_NAME, NAME, args...) \ + _class_##CLASS_NAME##_##NAME( \ + CLASS_NAME##_ptr_t self, ##args) + +#define PILE_ASSIGN_METHOD(CLASS_NAME, NAME) \ + self->NAME = _class_##CLASS_NAME##_##NAME; + +#define PILE_DEFINE_METHOD(CLASS_NAME, NAME, args...) \ + (*NAME)(CLASS_NAME##_ptr_t self, ##args) + +#define PILE_DEFINE_DESTRUCT(CLASS_NAME) \ + void (*destruct)(CLASS_NAME##_ptr_t self) + +#define PILE_CLASS_DESTRUCTOR(CLASS_NAME, args...) \ + void _class_##CLASS_NAME##_destruct( \ + CLASS_NAME##_ptr_t self, ##args) + +#define PILE_CLASS_DESTRUCTOR_DEFAULT(CLASS_NAME) \ + void _class_##CLASS_NAME##_destruct(void *self) \ + { \ + return; \ + } + +#define PILE_CALL(VARIABLE_NAME, METHOD_NAME, args...) \ + VARIABLE_NAME->METHOD_NAME(VARIABLE_NAME, ##args) + +#ifdef PILE_CLASS_SHORTCUTS + +#define class PILE_CLASS +#define new PILE_NEW +#define del PILE_DEL +#define impl_fn PILE_CLASS_METHOD +#define impl_construct PILE_CLASS_CONSTRUCTOR +#define impl_destruct PILE_CLASS_DESTRUCTOR +#define impl_default_destruct PILE_CLASS_DESTRUCTOR_DEFAULT +#define _assign PILE_ASSIGN_METHOD +#define def_fn PILE_DEFINE_METHOD +#define def_destruct PILE_DEFINE_DESTRUCT +#define call PILE_CALL + +#endif + +#endif + +#ifdef __cplusplus +} +#endif \ No newline at end of file diff --git a/pile_memory.h b/pile_memory.h new file mode 100644 index 0000000..8a1ae26 --- /dev/null +++ b/pile_memory.h @@ -0,0 +1,27 @@ +#ifndef _PILE_MEMORY_H_ +#define _PILE_MEMORY_H_ true + +#ifndef PILE_CUSTOM_ALLOC + +#ifndef _STDLIB_H_ +#define _STDLIB_H_ true +#include "stdlib.h" +#endif + +#ifndef _STRING_H_ +#define _STRING_H_ true +#include "string.h" +#endif + +#define PILE_MALLOC malloc +#define PILE_REALLOC realloc +#define PILE_FREE free +#define PILE_MEMCPY memcpy + +#endif + +#ifndef PILE_STRCPY +#define PILE_STRCPY strcpy +#endif + +#endif diff --git a/pile_runtime.c b/pile_runtime.c new file mode 100644 index 0000000..58b02f8 --- /dev/null +++ b/pile_runtime.c @@ -0,0 +1,3 @@ +#ifndef _PILE_RUNTIME_H_ +#include "pile_runtime.h" +#endif diff --git a/pile_runtime.h b/pile_runtime.h new file mode 100644 index 0000000..e49a0cc --- /dev/null +++ b/pile_runtime.h @@ -0,0 +1,13 @@ +#ifndef _PILE_RUNTIME_H_ +#define _PILE_RUNTIME_H_ true +#include "pile_string.h" + +typedef struct pile_module +{ + pile_string_t name; + void *content; +}; + +#include "pile_runtime.c" + +#endif diff --git a/pile_string.c b/pile_string.c new file mode 100644 index 0000000..1c63d5b --- /dev/null +++ b/pile_string.c @@ -0,0 +1,24 @@ +#ifndef _PILE_STRING_H_ +#include "pile_string.h" +#endif + +pile_int_t impl_fn(pile_string, reset, pile_str_t str) +{ + self->c_str = PILE_MALLOC(strlen(str)); + PILE_STRCPY(self->c_str, str); + self->length = strlen(str); + return self->length; +} + +impl_construct(pile_string, pile_str_t str) +{ + _assign(pile_string, reset); + self->reset(self, str); +} + +impl_destruct(pile_string) +{ + PILE_FREE(self->c_str); + + _assign(pile_string, reset); +} \ No newline at end of file diff --git a/pile_string.h b/pile_string.h new file mode 100644 index 0000000..b9a469a --- /dev/null +++ b/pile_string.h @@ -0,0 +1,21 @@ +#ifndef _PILE_STRING_H_ +#define _PILE_STRING_H_ true +#include "pile_types.h" +#define PILE_CLASS_SHORTCUTS true +#include "pile_class.h" + +class(pile_string) +{ + pile_int_t length; + pile_mut_str_t c_str; + + pile_int_t def_fn(pile_string, reset, pile_str_t str); + pile_int_t def_fn(pile_string, append, pile_char_t ch); + pile_int_t def_fn(pile_string, concat, pile_str_t str); + + def_destruct(pile_string); +}; + +#include "pile_string.c" + +#endif \ No newline at end of file diff --git a/pile_types.c b/pile_types.c new file mode 100644 index 0000000..d472ffe --- /dev/null +++ b/pile_types.c @@ -0,0 +1,12 @@ +#ifndef _PILE_TYPES_H_ +#include "pile_types.h" +#endif + +pile_container_t pile_make_container( + pile_type_t type, pile_any_t data) +{ + pile_container_t rslt; + rslt.content = data; + rslt.type = type; + return rslt; +} \ No newline at end of file diff --git a/pile_types.h b/pile_types.h new file mode 100644 index 0000000..ed44df1 --- /dev/null +++ b/pile_types.h @@ -0,0 +1,133 @@ +#ifndef _PILE_TYPES_H_ +#define _PILE_TYPES_H_ true + +/* Platform-Related Types : */ + +#ifndef PILE_PLATFORM_TYPE_INT +#define PILE_PLATFORM_TYPE_INT int +#endif +#ifndef PILE_PLATFORM_TYPE_LONG +#define PILE_PLATFORM_TYPE_LONG long long +#endif +#ifndef PILE_PLATFORM_TYPE_SHORT +#define PILE_PLATFORM_TYPE_SHORT short +#endif +#ifndef PILE_PLATFORM_TYPE_CHAR +#define PILE_PLATFORM_TYPE_CHAR char +#endif +#ifndef PILE_PLATFORM_TYPE_FLOAT +#define PILE_PLATFORM_TYPE_FLOAT float +#endif +#ifndef PILE_PLATFORM_TYPE_DOUBLE +#define PILE_PLATFORM_TYPE_DOUBLE double +#endif +#ifndef PILE_PLATFORM_TYPE_STR +#define PILE_PLATFORM_TYPE_STR const char * +#endif +#ifndef PILE_PLATFORM_TYPE_MUT_STR +#define PILE_PLATFORM_TYPE_MUT_STR char * +#endif +#ifndef PILE_PLATFORM_TYPE_BOOL +#define PILE_PLATFORM_TYPE_BOOL char +#endif + +#ifndef true +#define true 1 +#define false 0 +#endif + +typedef PILE_PLATFORM_TYPE_INT pile_int_t; +typedef PILE_PLATFORM_TYPE_LONG pile_long_t; +typedef PILE_PLATFORM_TYPE_SHORT pile_short_t; +typedef PILE_PLATFORM_TYPE_CHAR pile_char_t; +typedef PILE_PLATFORM_TYPE_FLOAT pile_float_t; +typedef PILE_PLATFORM_TYPE_DOUBLE pile_double_t; +typedef PILE_PLATFORM_TYPE_STR pile_str_t; +typedef PILE_PLATFORM_TYPE_MUT_STR pile_mut_str_t; +typedef PILE_PLATFORM_TYPE_BOOL pile_bool_t; + +typedef void *pile_any_t; + +/* End; */ + +/* Type Enums : */ + +#define PILE_TYPE_ENUM_BASE 10 + +typedef pile_short_t pile_type_t; + +#define PILE_TYPE_MODULE (PILE_TYPE_ENUM_BASE + 0) +#define PILE_TYPE_INT (PILE_TYPE_ENUM_BASE + 1) +#define PILE_TYPE_LONG (PILE_TYPE_ENUM_BASE + 2) +#define PILE_TYPE_SHORT (PILE_TYPE_ENUM_BASE + 4) +#define PILE_TYPE_CHAR (PILE_TYPE_ENUM_BASE + 5) +#define PILE_TYPE_FLOAT (PILE_TYPE_ENUM_BASE + 6) +#define PILE_TYPE_DOUBLE (PILE_TYPE_ENUM_BASE + 7) +#define PILE_TYPE_STR (PILE_TYPE_ENUM_BASE + 8) +#define PILE_TYPE_MUT_STR (PILE_TYPE_ENUM_BASE + 9) +#define PILE_TYPE_VECTOR (PILE_TYPE_ENUM_BASE + 10) +#define PILE_TYPE_STRING (PILE_TYPE_ENUM_BASE + 11) + +#ifndef _MACRO_CASE_INSENSITIVE +// In order to be compatible with PILE_VALUE_CONTAINER +#define pile_type_module PILE_TYPE_MODULE +#define pile_type_int PILE_TYPE_INT +#define pile_type_long PILE_TYPE_LONG +#define pile_type_short PILE_TYPE_SHORT +#define pile_type_char PILE_TYPE_CHAR +#define pile_type_float PILE_TYPE_FLOAT +#define pile_type_double PILE_TYPE_DOUBLE +#define pile_type_str PILE_TYPE_STR +#define pile_type_mut_str PILE_TYPE_MUT_STR +#define pile_type_vector PILE_TYPE_VECTOR +#define pile_type_string PILE_TYPE_STRING +#endif + +/* End; */ + +/* Pile Containers: */ + +typedef struct pile_container +{ + void *content; + pile_type_t type; + union { + pile_int_t v_int; + pile_short_t v_short; + pile_long_t v_long; + pile_float_t v_float; + pile_str_t v_str; + pile_mut_str_t v_mut_str; + pile_double_t v_double; + pile_bool_t v_bool; + pile_char_t v_char; + } values; +} pile_container_t; + +typedef pile_container_t *pile_container_ptr_t; + +#define PILE_MAKE_PTR(type, name, data) \ + type *name = &data + +#define PILE_MAKE_PTR_LITERAL(name, data) \ + typeof(data) name##_origin = data; \ + PILE_MAKE_PTR(typeof(data), name, name##_origin); + +#define PILE_MAKE_PTR_LITERAL_CONTAINER(type, name, data) \ + PILE_MAKE_PTR_LITERAL(name##_prototype, data) \ + pile_container_t name = \ + pile_make_container(type, name##_prototype) + +#define PILE_VALUE_CONTAINER(v_type, data) \ + { \ + .type = pile_type_##v_type, \ + .values = { \ + .v_##v_type = data, \ + }, \ + } + +/* End; */ + +#include "pile_types.c" + +#endif \ No newline at end of file diff --git a/pile_vector.c b/pile_vector.c new file mode 100644 index 0000000..483e627 --- /dev/null +++ b/pile_vector.c @@ -0,0 +1,110 @@ +#ifndef _PILE_VECTOR_H_ +#include "pile_vector.h" +#endif + +pile_int_t impl_fn(pile_vector, resize, pile_int_t size) +{ + self->size = size; + PILE_REALLOC(self->data, size * sizeof(pile_container_t)); + return self->size; +} + +pile_int_t impl_fn(pile_vector, push, pile_container_t item) +{ + if (self->end >= self->size) + { + self->resize(self, self->end + 1); + } + self->data[self->end] = item; + self->end++; + return self->end; +} + +pile_int_t impl_fn(pile_vector, pop) +{ + if (self->end == self->size) + { + self->resize(self, self->size - 1); + } + self->end--; + return self->end; +} + +pile_container_t impl_fn(pile_vector, top) +{ + return self->data[self->end - 1]; +} + +pile_container_t impl_fn(pile_vector, bottom) +{ + return self->data[0]; +} + +pile_int_t impl_fn(pile_vector, append, pile_vector_ptr_t vec) +{ + pile_int_t new_size = self->end + vec->end; + if (new_size > self->size) + { + self->resize(self, new_size); + } + PILE_MEMCPY(self->data + self->end, vec->data, + vec->end * sizeof(pile_container_t)); + self->end = new_size; + return self->end; +} + +pile_bool_t impl_fn(pile_vector, is_empty) +{ + return (self->end == 0); +} + +pile_int_t impl_fn(pile_vector, slice, + pile_int_t start, pile_int_t length) +{ + pile_container_ptr_t origin = self->data; + self->data = (pile_container_ptr_t) + PILE_MALLOC(length * sizeof(pile_container_t)); + PILE_MEMCPY(self->data, origin + start, + length * sizeof(pile_container_t)); + self->size -= start; + self->end = length; + PILE_FREE(origin); + return length; +} + +pile_int_t impl_fn(pile_vector, insert, + pile_int_t pos, pile_container_t val) +{ + if (self->end >= self->size) + { + self->resize(self, self->size + 1); + } + PILE_MEMCPY(self->data + pos + 1, + self->data + pos, + (self->end - pos) * sizeof(pile_container_t)); + self->data[pos] = val; + self->end++; + return self->end; +} + +impl_construct(pile_vector, pile_int_t size) +{ + self->size = size; + self->end = 0; + self->data = (pile_container_ptr_t) + PILE_MALLOC(size * sizeof(pile_container_t)); + _assign(pile_vector, push); + _assign(pile_vector, resize); + _assign(pile_vector, pop); + _assign(pile_vector, top); + _assign(pile_vector, bottom); + _assign(pile_vector, append); + _assign(pile_vector, is_empty); + _assign(pile_vector, slice); + _assign(pile_vector, insert); +} + +impl_destruct(pile_vector) +{ + PILE_FREE(self->data); +} \ No newline at end of file diff --git a/pile_vector.h b/pile_vector.h new file mode 100644 index 0000000..e37fa59 --- /dev/null +++ b/pile_vector.h @@ -0,0 +1,33 @@ +#ifndef _PILE_VECTOR_H_ +#define _PILE_VECTOR_H_ true +#include "pile_types.h" +#define PILE_CLASS_SHORTCUTS true +#include "pile_class.h" +#include "pile_memory.h" +#pragma GCC diagnostic ignored "-Wunused-result" + +class(pile_vector) +{ + pile_int_t size; + pile_int_t end; + pile_container_ptr_t data; + pile_type_t type; + + pile_int_t def_fn(pile_vector, resize, pile_int_t size); + pile_int_t def_fn(pile_vector, push, pile_container_t item); + pile_int_t def_fn(pile_vector, append, pile_vector_ptr_t vec); + pile_int_t def_fn(pile_vector, pop); + pile_container_t def_fn(pile_vector, top); + pile_container_t def_fn(pile_vector, bottom); + pile_bool_t def_fn(pile_vector, is_empty); + pile_int_t def_fn(pile_vector, slice, + pile_int_t start, pile_int_t length); + pile_int_t def_fn(pile_vector, insert, + pile_int_t pos, pile_container_t val); + + def_destruct(pile_vector); +}; + +#include "pile_vector.c" + +#endif \ No newline at end of file diff --git a/tests/test_vector.c b/tests/test_vector.c new file mode 100644 index 0000000..40c745f --- /dev/null +++ b/tests/test_vector.c @@ -0,0 +1,35 @@ +#include +#include "pile_vector.h" + +int main() +{ + printf("compile_successful\r\n"); + new (pile_vector, arr, 0); + PILE_MAKE_PTR_LITERAL(a, 80); + PILE_MAKE_PTR_LITERAL(b, 90); + PILE_MAKE_PTR_LITERAL(c, 20); + PILE_MAKE_PTR_LITERAL(d, 10); + PILE_MAKE_PTR_LITERAL(e, 30); + arr->push(arr, pile_make_container(PILE_TYPE_INT, a)); + call(arr, resize, 10); + arr->push(arr, pile_make_container(PILE_TYPE_INT, a)); + arr->push(arr, pile_make_container(PILE_TYPE_INT, a)); + arr->push(arr, pile_make_container(PILE_TYPE_INT, b)); + arr->push(arr, pile_make_container(PILE_TYPE_INT, a)); + arr->push(arr, pile_make_container(PILE_TYPE_INT, b)); + arr->push(arr, pile_make_container(PILE_TYPE_INT, c)); + arr->push(arr, pile_make_container(PILE_TYPE_INT, d)); + arr->push(arr, pile_make_container(PILE_TYPE_INT, e)); + PILE_MAKE_PTR_LITERAL_CONTAINER(PILE_TYPE_INT, f, 12); + call(arr, push, f); + arr->slice(arr, 1, 3); + arr->insert(arr, 1, f); + while (!arr->is_empty(arr)) + { + printf("%d ", *((int *)arr->top(arr).content)); + call(arr, pop); + } + del(arr); + printf("\r\n"); + return 0; +} \ No newline at end of file