diff options
author | wens <wens@63ad8ddf-47c3-0310-b6dd-a9e9d9715204> | 2008-06-15 22:34:06 +0800 |
---|---|---|
committer | wens <wens@63ad8ddf-47c3-0310-b6dd-a9e9d9715204> | 2008-06-15 22:34:06 +0800 |
commit | ddcba43d911f6a5faae9130073820e4442b9d4c8 (patch) | |
tree | fb06899708c9cc92654fcca8d298ef61419f886f | |
parent | 2b17144356fc625165400e7a856ad76cae4bf4b2 (diff) | |
download | pttbbs-ddcba43d911f6a5faae9130073820e4442b9d4c8.tar pttbbs-ddcba43d911f6a5faae9130073820e4442b9d4c8.tar.gz pttbbs-ddcba43d911f6a5faae9130073820e4442b9d4c8.tar.bz2 pttbbs-ddcba43d911f6a5faae9130073820e4442b9d4c8.tar.lz pttbbs-ddcba43d911f6a5faae9130073820e4442b9d4c8.tar.xz pttbbs-ddcba43d911f6a5faae9130073820e4442b9d4c8.tar.zst pttbbs-ddcba43d911f6a5faae9130073820e4442b9d4c8.zip |
General vector-like list
git-svn-id: http://opensvn.csie.org/pttbbs/trunk/pttbbs@4357 63ad8ddf-47c3-0310-b6dd-a9e9d9715204
-rw-r--r-- | common/sys/Makefile | 2 | ||||
-rw-r--r-- | common/sys/vector.c | 161 | ||||
-rw-r--r-- | include/cmsys.h | 21 |
3 files changed, 183 insertions, 1 deletions
diff --git a/common/sys/Makefile b/common/sys/Makefile index e0fec71f..574ab582 100644 --- a/common/sys/Makefile +++ b/common/sys/Makefile @@ -5,7 +5,7 @@ MKPIC:=no SRCROOT= ../.. .include "$(SRCROOT)/pttbbs.mk" -SRCS:= file.c lock.c log.c net.c sort.c string.c time.c crypt.c record.c osdep.c +SRCS:= file.c lock.c log.c net.c sort.c string.c time.c crypt.c record.c osdep.c vector.c LIB:= cmsys install: diff --git a/common/sys/vector.c b/common/sys/vector.c new file mode 100644 index 00000000..e5ed9346 --- /dev/null +++ b/common/sys/vector.c @@ -0,0 +1,161 @@ +/* $Id$ */ +#include <stdlib.h> +#include <string.h> +#include <assert.h> +#include "cmsys.h" + +#define chartoupper(c) ((c >= 'a' && c <= 'z') ? c+'A'-'a' : c) + +void +Vector_init(struct Vector *self, const int size) +{ + assert(size != 0); + self->size = size; + self->length = 0; + self->capacity = 0; + self->base = NULL; +} + +void +Vector_delete(struct Vector *self) +{ + self->length = 0; + self->capacity = 0; + if (self->base) + free(self->base); + self->base = NULL; +} + +void +Vector_clear(struct Vector *self, const int size) +{ + Vector_delete(self); + Vector_init(self, size); +} + +int +Vector_length(struct Vector *self) +{ + return self->length; +} + +void +Vector_resize(struct Vector *self, const int length) +{ + int capacity = length * self->size; +#define MIN_CAPACITY 4096 + if (capacity == 0) { + if (self->base) + free(self->base); + self->base = NULL; + self->capacity = 0; + } else { + int old_capacity = self->capacity; + assert(capacity > 0); + if (self->capacity == 0) + self->capacity = MIN_CAPACITY; + //if (self->capacity > capacity && self->capacity > MIN_CAPACITY) + // self->capacity /= 2; + while (self->capacity < capacity) + self->capacity *= 2; + + if (old_capacity != self->capacity || self->base == NULL) { + char *tmp = (char *)realloc(self->base, self->capacity); + assert(tmp); + self->base = tmp; + } + } +} + +void +Vector_add(struct Vector *self, const char *name) +{ + Vector_resize(self, self->length+1); + strlcpy(self->base + self->size * self->length, name, self->size); + self->length++; +} + +const char* +Vector_get(struct Vector *self, const int idx) +{ + assert(0 <= idx && idx < self->length); + return self->base + self->size * idx; +} + +int +Vector_MaxLen(const struct Vector *list, const int offset, const int count) +{ + int i; + int maxlen = 0; + + for(i=offset; i<list->length; i++) { + int len = strlen(list->base + list->size * i); + if (len > maxlen) + maxlen = len; + } + assert(maxlen <= list->size); + return maxlen; +} + +int +Vector_match(const struct Vector *src, struct Vector *dst, const int key, const int pos) +{ + int uckey, lckey; + int i; + + Vector_clear(dst, src->size); + + uckey = chartoupper(key); + if (key >= 'A' && key <= 'Z') + lckey = key | 0x20; + else + lckey = key; + + for (i=0; i<src->length; i++) { + int ch = src->base[src->size * i + pos]; + if (ch == lckey || ch == uckey) + Vector_add(dst, src->base + src->size * i); + } + + return dst->length; +} + +void +Vector_sublist(struct Vector *src, struct Vector *dst, const char *tag) +{ + int i; + int len; + Vector_clear(dst, src->size); + + len = strlen(tag); + for (i=0; i<src->length; i++) + if (len==0 || strncasecmp(src->base + src->size * i, tag, len)==0) + Vector_add(dst, src->base + src->size * i); +} + +int +Vector_remove(struct Vector *self, const char *name) +{ + int i; + for (i=0; i<self->length; i++) + if (strcasecmp(self->base + self->size * i, name) == 0) { + strlcpy(self->base + self->size * i, + self->base + self->size * (self->length-1), self->size); + + self->length--; + Vector_resize(self, self->length); + return 1; + } + return 0; +} + +int +Vector_search(const struct Vector *self, const char *name) +{ + int i; + for (i=0; i<self->length; i++) + if (strcasecmp(self->base + self->size * i, name) == 0) + return 1; + return 0; +} + diff --git a/include/cmsys.h b/include/cmsys.h index 1e866630..2a219324 100644 --- a/include/cmsys.h +++ b/include/cmsys.h @@ -147,4 +147,25 @@ int delete_records(const char *fpath, size_t size, int id, size_t num); #define delete_record(fpath, size, id) delete_records(fpath, size, id, 1) int apply_record(const char *fpath, int (*fptr) (void *item, void *optarg), size_t size, void *arg); +/* vector.c */ +struct Vector { + int size; + int length; + int capacity; + char *base; +}; + +void Vector_init(struct Vector *self, const int size); +void Vector_delete(struct Vector *self); +void Vector_clear(struct Vector *self, const int size); +int Vector_length(struct Vector *self); +void Vector_resize(struct Vector *self, const int length); +void Vector_add(struct Vector *self, const char *name); +const char* Vector_get(struct Vector *self, const int idx); +int Vector_MaxLen(const struct Vector *list, const int offset, const int count); +int Vector_match(const struct Vector *src, struct Vector *dst, const int key, const int pos); +void Vector_sublist(struct Vector *src, struct Vector *dst, const char *tag); +int Vector_remove(struct Vector *self, const char *name); +int Vector_search(const struct Vector *self, const char *name); + #endif |