summaryrefslogtreecommitdiffstats
path: root/hw1/basic-array.c
diff options
context:
space:
mode:
authorLAN-TW <lantw44@gmail.com>2013-10-23 02:07:30 +0800
committerLAN-TW <lantw44@gmail.com>2013-10-23 02:07:30 +0800
commit0cd8997ea2de12bf7da2cabc6956f4a008e18c7c (patch)
tree5ecf5e84e13abecbdeb491e4ba256aa252d9a2a9 /hw1/basic-array.c
parenta490b98a996d16aa9544f7144e02034c04c50f59 (diff)
downloadcn2013-0cd8997ea2de12bf7da2cabc6956f4a008e18c7c.tar.gz
cn2013-0cd8997ea2de12bf7da2cabc6956f4a008e18c7c.tar.zst
cn2013-0cd8997ea2de12bf7da2cabc6956f4a008e18c7c.zip
HW1: 加入使用者身份相關內容
Diffstat (limited to 'hw1/basic-array.c')
-rw-r--r--hw1/basic-array.c133
1 files changed, 133 insertions, 0 deletions
diff --git a/hw1/basic-array.c b/hw1/basic-array.c
new file mode 100644
index 0000000..5d5f61e
--- /dev/null
+++ b/hw1/basic-array.c
@@ -0,0 +1,133 @@
+#include "xwrap.h"
+#include <stdlib.h>
+#include <string.h>
+#include "basic-array.h"
+
+Array* array_create_setmax(int itemsize, int len, int maxlen){
+ if(itemsize <= 0 || len < 0 || maxlen < len){
+ return NULL;
+ }
+ Array* arr = (Array*)xmalloc(sizeof(Array));
+ if(arr == NULL){
+ return NULL;
+ }
+ arr->arr_itemsize = itemsize;
+ arr->arr_curlen = len;
+ arr->arr_maxlen = maxlen;
+ if(maxlen != 0){
+ arr->arr_data = xmalloc(itemsize * maxlen);
+ if(arr->arr_data == NULL){
+ free(arr);
+ return NULL;
+ }
+ }else{
+ arr->arr_data = NULL;
+ }
+ return arr;
+}
+
+Array* array_create(int itemsize, int len){
+ return array_create_setmax(itemsize, len, len);
+}
+
+void array_free(Array* arr){
+ if(arr->arr_data != NULL){
+ free(arr->arr_data);
+ }
+ free(arr);
+}
+
+int array_pushback(Array* arr, const void* data){
+ if((arr->arr_maxlen) < (arr->arr_curlen + 1)){
+ if(arr->arr_maxlen != 0){
+ if(array_setmax(arr, arr->arr_maxlen*2) < 0){
+ return -1;
+ }
+ }else{
+ if(array_setmax(arr, 1) < 0){
+ return -1;
+ }
+ }
+ }
+ memcpy(array_vp(arr, arr->arr_curlen), data, arr->arr_itemsize);
+ arr->arr_curlen++;
+ return 0;
+}
+
+int array_setlen(Array* arr, int len){
+ if(len > (arr->arr_maxlen)){
+ if(array_setmax(arr, len) < 0){
+ return -1;
+ }else{
+ arr->arr_curlen = len;
+ }
+ }else{
+ arr->arr_curlen = len;
+ return 0;
+ }
+ return 0;
+}
+
+int array_setmax(Array* arr, int max){
+ void* newptr;
+ if(arr->arr_data == NULL){
+ newptr = xmalloc((arr->arr_itemsize)*max);
+ if(newptr == NULL){
+ return -1;
+ }else{
+ arr->arr_maxlen = max;
+ arr->arr_data = newptr;
+ return 0;
+ }
+ }
+ newptr = realloc(arr->arr_data, (arr->arr_itemsize)*max);
+ if(newptr == NULL){
+ return -1;
+ }else{
+ arr->arr_maxlen = max;
+ arr->arr_data = newptr;
+ }
+ return 0;
+}
+
+int array_strip(Array* arr){
+ if(arr->arr_data == NULL){
+ return 0;
+ }
+ Array* newptr;
+ /* 其實縮小空間營該一定會成功才對......
+ * 不過還是保險一點,加個判斷式,別說 memory leak 是我害的
+ * 當然也是避免編譯器一直跳 warning
+ */
+ if((arr->arr_maxlen) > (arr->arr_curlen)){
+ arr->arr_maxlen = arr->arr_curlen;
+ newptr = realloc(arr->arr_data, (arr->arr_curlen)*(arr->arr_itemsize));
+ if(newptr == NULL){
+ return -1;
+ }
+ arr->arr_data = newptr;
+ }
+ return 0;
+}
+
+/* 基本上直接玩 struct 的函式還是少用吧 */
+void* array_drop_struct(Array* arr){
+ void* toreturn = arr->arr_data;
+ free(arr);
+ return toreturn;
+}
+
+Array* array_make_struct(void* data, int itemsize, int len, int maxlen){
+ if(itemsize <= 0 || len < 0 || maxlen < len){
+ return NULL;
+ }
+ Array* arr = (Array*)xmalloc(sizeof(Array));
+ if(arr == NULL){
+ return NULL;
+ }
+ arr->arr_itemsize = itemsize;
+ arr->arr_curlen = len;
+ arr->arr_maxlen = maxlen;
+ arr->arr_data = data;
+ return arr;
+}