stack添加单侧

This commit is contained in:
建峰 2024-08-30 00:49:50 +08:00
parent 87ff4b4127
commit 03f4396227
8 changed files with 406 additions and 109 deletions

View File

@ -2,7 +2,7 @@
#ifndef _UNITY_CONFIG_H_ #ifndef _UNITY_CONFIG_H_
#define _UNITY_CONFIG_H_ #define _UNITY_CONFIG_H_
// #define UNITY_OUTPUT_COLOR 1 #define UNITY_OUTPUT_COLOR 1
#define UNITY_USE_FLUSH_STDOUT 1 #define UNITY_USE_FLUSH_STDOUT 1
#define UNITY_INCLUDE_PRINT_FORMATTED 1 // support TEST_PRINTF #define UNITY_INCLUDE_PRINT_FORMATTED 1 // support TEST_PRINTF

View File

@ -11,7 +11,7 @@
#ifndef _COMMON_H_ #ifndef _COMMON_H_
#define _COMMON_H_ #define _COMMON_H_
#define NDEBUG 1 // #define NDEBUG 1
#include <stdint.h> #include <stdint.h>
#include <stdbool.h> #include <stdbool.h>

View File

@ -39,13 +39,14 @@ struct _queue
bool (*back)(struct _queue* self, void* obj); bool (*back)(struct _queue* self, void* obj);
bool (*front)(struct _queue* self, void* obj); bool (*front)(struct _queue* self, void* obj);
bool (*clear)(struct _queue* self); // base
bool (*empty)(struct _queue* self); bool (*empty)(struct _queue* self);
bool (*full)(struct _queue* self); bool (*full)(struct _queue* self);
uint32_t (*size)(struct _queue* self); uint32_t (*size)(struct _queue* self);
uint32_t (*capacity)(struct _queue* self); uint32_t (*capacity)(struct _queue* self);
// clear and free node pointer // clear and free node
bool (*clear)(struct _queue* self);
void (*destory)(struct _queue* self); void (*destory)(struct _queue* self);
// print // print

View File

@ -34,10 +34,11 @@ struct _stack
bool (*pop)(struct _stack* self, void* obj); bool (*pop)(struct _stack* self, void* obj);
// base // base
uint32_t(*size)(struct _stack* self);
bool (*empty)(struct _stack* self); bool (*empty)(struct _stack* self);
uint32_t (*size)(struct _stack* self);
uint32_t (*capacity)(struct _stack* self);
// others // clear and free node
bool (*clear)(struct _stack* self); bool (*clear)(struct _stack* self);
void (*destory)(struct _stack* self); void (*destory)(struct _stack* self);

View File

@ -117,6 +117,11 @@ static bool queue_front(struct _queue* self, void* obj)
static bool queue_clear(struct _queue* self) static bool queue_clear(struct _queue* self)
{ {
assert(self != NULL); assert(self != NULL);
if(self->empty(self))
{
return true;
}
struct _queue_node* node = self->_front; struct _queue_node* node = self->_front;
struct _queue_node* next = NULL; struct _queue_node* next = NULL;
while (node) while (node)
@ -301,97 +306,97 @@ static void queue2_print(struct _queue* self)
} }
} }
bool queue_init(struct _queue * queue, uint32_t obj_size) bool queue_init(struct _queue * self, uint32_t obj_size)
{ {
assert(queue != NULL); assert(self != NULL);
assert(obj_size > 0); assert(obj_size > 0);
if(queue == NULL || obj_size == 0) if(self == NULL || obj_size == 0)
{ {
return false; return false;
} }
// attribute init // attribute init
queue->_size = 0; self->_size = 0;
queue->_obj_size = obj_size; self->_obj_size = obj_size;
queue->_capacity = UINT32_MAX; self->_capacity = UINT32_MAX;
queue->_ratio = 1; self->_ratio = 1;
// function init // function init
queue->push = queue_push; self->push = queue_push;
queue->pop = queue_pop; self->pop = queue_pop;
queue->back = queue_back; self->back = queue_back;
queue->front = queue_front; self->front = queue_front;
queue->clear = queue_clear; self->clear = queue_clear;
queue->empty = queue_empty; self->empty = queue_empty;
queue->full = queue_full; self->full = queue_full;
queue->size = queue_size; self->size = queue_size;
queue->capacity = queue_capacity; self->capacity = queue_capacity;
queue->destory = queue_destory; self->destory = queue_destory;
queue->print = queue_print; self->print = queue_print;
// init front & back // init front & back
queue->_front = NULL; self->_front = NULL;
queue->_back = NULL; self->_back = NULL;
return true; return true;
} }
bool queue_init2(struct _queue * queue, uint32_t obj_size, uint32_t capacity) bool queue_init2(struct _queue * self, uint32_t obj_size, uint32_t capacity)
{ {
assert(queue != NULL); assert(self != NULL);
assert(obj_size > 0); assert(obj_size > 0);
assert(capacity > 0); assert(capacity > 0);
if(queue == NULL || obj_size == 0 || capacity == 0) if(self == NULL || obj_size == 0 || capacity == 0)
{ {
return false; return false;
} }
// attribute init // attribute init
queue->_size = 0; self->_size = 0;
queue->_obj_size = obj_size; self->_obj_size = obj_size;
queue->_capacity = capacity; self->_capacity = capacity;
queue->_ratio = 2; self->_ratio = 2;
// function init // function init
queue->push = queue2_push; self->push = queue2_push;
queue->pop = queue2_pop; self->pop = queue2_pop;
queue->back = queue2_back; self->back = queue2_back;
queue->front = queue2_front; self->front = queue2_front;
queue->clear = queue2_clear; self->clear = queue2_clear;
queue->empty = queue_empty; self->empty = queue_empty;
queue->full = queue_full; self->full = queue_full;
queue->size = queue_size; self->size = queue_size;
queue->capacity = queue_capacity; self->capacity = queue_capacity;
queue->destory = queue2_destory; self->destory = queue2_destory;
queue->print = queue2_print; self->print = queue2_print;
// init front & back // init front & back
queue->_front = (struct _queue_node *)malloc(sizeof(struct _queue_node)); self->_front = (struct _queue_node *)malloc(sizeof(struct _queue_node));
if(queue->_front == NULL) if(self->_front == NULL)
{ {
goto done; goto done;
} }
queue->_back = queue->_front; self->_back = self->_front;
// use queue->_front->obj as obj_array // use self->_front->obj as obj_array
// queue->_front->obj = calloc(queue->_capacity, queue->_obj_size); // self->_front->obj = calloc(self->_capacity, self->_obj_size);
queue->_front->obj = malloc(queue->_capacity * queue->_obj_size); self->_front->obj = malloc(self->_capacity * self->_obj_size);
if(queue->_front->obj == NULL) if(self->_front->obj == NULL)
{ {
goto done1; goto done1;
} }
queue->_index_front = 0; self->_index_front = 0;
queue->_index_back = 0; self->_index_back = 0;
return true; return true;
done1: done1:
free(queue->_front); free(self->_front);
done: done:
return false; return false;
} }
@ -403,10 +408,7 @@ queue_t queue_new(void)
void queue_free(queue_t* queue) void queue_free(queue_t* queue)
{ {
// assert(queue != NULL); assert(queue != NULL);
// assert(*queue != NULL);
// assert((*queue)->destory != NULL);
if(queue != NULL && *queue != NULL) if(queue != NULL && *queue != NULL)
{ {
if((*queue)->destory != NULL) if((*queue)->destory != NULL)

View File

@ -25,9 +25,7 @@ static uint32_t stack_size(struct _stack* self)
static bool stack_empty(struct _stack* self) static bool stack_empty(struct _stack* self)
{ {
assert(self != NULL); assert(self != NULL);
// assert(self->_head != NULL); return stack_size(self) == 0;
// return self->_head->next == NULL ? true : false;
return !stack_size(self);
} }
static bool stack_peek(struct _stack* self, void* obj) static bool stack_peek(struct _stack* self, void* obj)
@ -105,10 +103,9 @@ static bool stack_pop(struct _stack* self, void* obj)
static bool stack_clear(struct _stack* self) static bool stack_clear(struct _stack* self)
{ {
assert(self != NULL); assert(self != NULL);
if (self->empty(self)) if (self->empty(self))
{ {
return false; return true;
} }
struct _stack_node* node = self->_head->next; struct _stack_node* node = self->_head->next;
@ -149,42 +146,6 @@ static void stack_print(struct _stack* self)
} }
} }
bool stack_init(struct _stack* self, uint32_t obj_size)
{
assert(self != NULL);
// 1. set attr
self->_obj_size = obj_size;
self->_size = 0;
// self->_capacity = 64; // ÎÞЧ
// self->_ratio = 2; // ÎÞЧ
// 2. set function
// kernel
self->peek = stack_peek;
self->pop = stack_pop;
self->push = stack_push;
// others
self->clear = stack_clear;
self->empty = stack_empty;
self->size = stack_size;
self->destory = stack_destory;
self->print = stack_print;
// 3. set node
self->_head = (struct _stack_node *)malloc(sizeof(struct _stack_node));
if (self->_head == NULL)
{
return false;
}
self->_head->obj = NULL;
self->_head->next = NULL;
return true;
}
static bool stack2_peek(struct _stack* self, void* obj) static bool stack2_peek(struct _stack* self, void* obj)
{ {
assert(self != NULL); assert(self != NULL);
@ -208,9 +169,9 @@ static bool stack2_push(struct _stack* self, void* obj)
assert(self->_head != NULL); assert(self->_head != NULL);
assert(obj != NULL); assert(obj != NULL);
if (self->size(self) == self->_capacity) if (self->size(self) == self->capacity(self))
{ {
void* obj_new = (void*)realloc(self->_head->obj, self->_capacity * self->_obj_size * self->_ratio); void* obj_new = (void*)realloc(self->_head->obj, self->capacity(self) * self->_obj_size * self->_ratio);
if (obj_new == NULL) if (obj_new == NULL)
{ {
return false; return false;
@ -281,6 +242,51 @@ static void stack2_print(struct _stack* self)
} }
} }
bool stack_init(struct _stack* self, uint32_t obj_size)
{
assert(self != NULL);
assert(obj_size != 0);
if(self == NULL || obj_size == 0)
{
return false;
}
// 1. set attr
self->_obj_size = obj_size;
self->_size = 0;
self->_capacity = UINT32_MAX;
self->_ratio = 1;
// 2. set function
// kernel
self->peek = stack_peek;
self->pop = stack_pop;
self->push = stack_push;
// base
self->empty = stack_empty;
self->size = stack_size;
self->capacity = stack_capacity;
// clear and free node
self->clear = stack_clear;
self->destory = stack_destory;
// print
self->print = stack_print;
// 3. set node
self->_head = (struct _stack_node *)malloc(sizeof(struct _stack_node));
if (self->_head == NULL)
{
return false;
}
self->_head->obj = NULL;
self->_head->next = NULL;
return true;
}
bool stack_init2(struct _stack* self, uint32_t obj_size, uint32_t capacity) bool stack_init2(struct _stack* self, uint32_t obj_size, uint32_t capacity)
{ {
assert(self != NULL); assert(self != NULL);
@ -298,10 +304,14 @@ bool stack_init2(struct _stack* self, uint32_t obj_size, uint32_t capacity)
self->push = stack2_push; self->push = stack2_push;
// others // others
self->clear = stack_clear;
self->empty = stack_empty; self->empty = stack_empty;
self->size = stack_size; self->size = stack_size;
self->capacity = stack_capacity;
// clear and free node
self->clear = stack_clear;
self->destory = stack2_destory; self->destory = stack2_destory;
// print
self->print = stack2_print; self->print = stack2_print;
// 3. set node // 3. set node
@ -324,15 +334,19 @@ bool stack_init2(struct _stack* self, uint32_t obj_size, uint32_t capacity)
stack_t stack_new(void) stack_t stack_new(void)
{ {
return (struct _stack*)malloc(sizeof(struct _stack)); return (struct _stack*)calloc(1, sizeof(struct _stack));
} }
void stack_free(stack_t *stack) void stack_free(stack_t *stack)
{ {
if(*stack) assert(stack != NULL);
if(stack != NULL && *stack != NULL)
{
if((*stack)->destory != NULL)
{ {
(*stack)->destory(*stack); (*stack)->destory(*stack);
free(*stack);
} }
free(*stack);
*stack = NULL; *stack = NULL;
}
} }

View File

@ -73,8 +73,8 @@ int main(int argc, char const *argv[])
printf("----- Unicstl Unit Test -----\n"); printf("----- Unicstl Unit Test -----\n");
UNITY_BEGIN(); UNITY_BEGIN();
// test_stack();
test_queue(); test_queue();
test_stack();
return UNITY_END(); return UNITY_END();
} }

View File

@ -10,6 +10,257 @@
*/ */
#include "test.h" #include "test.h"
static void test_stack_init(void)
{
struct _stack stack;
// ------------------------------
#ifdef NDEBUG
TEST_ASSERT_FALSE(stack_init(NULL, sizeof(int)));
TEST_ASSERT_FALSE(stack_init(&stack, 0));
#endif
TEST_ASSERT_TRUE(stack_init(&stack, sizeof(int)));
stack.destory(&stack);
// ------------------------------
#ifdef NDEBUG
TEST_ASSERT_FALSE(stack_init2(NULL, sizeof(int), 1));
TEST_ASSERT_FALSE(stack_init2(&stack, 0, 1));
TEST_ASSERT_FALSE(stack_init2(&stack, sizeof(int), 0));
#endif
TEST_ASSERT_TRUE(stack_init2(&stack, sizeof(int), 1));
stack.destory(&stack);
}
static void test_stack_new(void)
{
stack_t stack = NULL;
stack = stack_new();
stack_free(&stack);
// ------------------------------
stack = stack_new();
TEST_ASSERT_NOT_NULL(stack);
#ifdef NDEBUG
TEST_ASSERT_FALSE(stack_init(NULL, sizeof(int)));
TEST_ASSERT_FALSE(stack_init(stack, 0));
#endif
TEST_ASSERT_TRUE(stack_init(stack, sizeof(int)));
stack_free(&stack);
// ------------------------------
stack = stack_new();
TEST_ASSERT_NOT_NULL(stack);
#ifdef NDEBUG
TEST_ASSERT_FALSE(stack_init2(NULL, sizeof(int), 1));
TEST_ASSERT_FALSE(stack_init2(stack, 0, 1));
TEST_ASSERT_FALSE(stack_init2(stack, sizeof(int), 0));
#endif
TEST_ASSERT_TRUE(stack_init2(stack, sizeof(int), 1));
stack_free(&stack);
TEST_ASSERT_NULL(stack);
stack_free(&stack); // stack_free(NULL);
}
static void test_stack_push(void)
{
int temp = 0;
int data[] = { 1,2,3,4,5,6,7,8,9,10 };
uint32_t len = sizeof(data) / sizeof(data[0]);
uint32_t i = 0;
stack_t stack = NULL;
// ------------------------------
stack = stack_new();
stack_init(stack, sizeof(int));
TEST_ASSERT_TRUE(stack->empty(stack));
for(i = 0; i < len; i++)
{
TEST_ASSERT_TRUE(stack->push(stack, &data[i]));
TEST_ASSERT_EQUAL_INT(i + 1, stack->size(stack));
TEST_ASSERT_TRUE(stack->peek(stack, &temp));
TEST_ASSERT_EQUAL_INT(data[i], temp);
TEST_ASSERT_FALSE(stack->empty(stack));
}
stack_free(&stack);
// ------------------------------
stack = stack_new();
stack_init2(stack, sizeof(int), len);
TEST_ASSERT_TRUE(stack->empty(stack));
for(i = 0; i < len; i++)
{
TEST_ASSERT_TRUE(stack->push(stack, &data[i]));
TEST_ASSERT_EQUAL_INT(i + 1, stack->size(stack));
TEST_ASSERT_TRUE(stack->peek(stack, &temp));
TEST_ASSERT_EQUAL_INT(data[i], temp);
TEST_ASSERT_FALSE(stack->empty(stack));
}
stack_free(&stack);
// ------------------------------
// if capacity is less than data len
stack = stack_new();
stack_init2(stack, sizeof(int), len - 2);
for(i = 0; i < len; i++)
{
TEST_ASSERT_TRUE(stack->push(stack, &data[i]));
TEST_ASSERT_EQUAL_INT(i + 1, stack->size(stack));
}
stack_free(&stack);
}
static void test_stack_pop(void)
{
int temp = 0;
int data[] = { 1,2,3,4,5,6,7,8,9,10 };
uint32_t len = sizeof(data) / sizeof(data[0]);
uint32_t i = 0;
stack_t stack = NULL;
// ------------------------------
stack = stack_new();
stack_init(stack, sizeof(int));
for(i = 0; i < len; i++)
{
stack->push(stack, &data[i]);
}
for (i = 0; i < len; i++)
{
TEST_ASSERT_TRUE(stack->peek(stack, &temp));
TEST_ASSERT_EQUAL_INT(data[stack->size(stack) - 1], temp);
TEST_ASSERT_TRUE(stack->pop(stack, &temp));
if (!stack->empty(stack))
{
TEST_ASSERT_TRUE(stack->peek(stack, &temp));
TEST_ASSERT_EQUAL_INT(data[stack->size(stack) - 1], temp);
}
else
{
TEST_ASSERT_FALSE(stack->peek(stack, &temp));
}
}
TEST_ASSERT_TRUE(stack->empty(stack));
TEST_ASSERT_FALSE(stack->pop(stack, &temp));
stack_free(&stack);
// ------------------------------
stack = stack_new();
stack_init2(stack, sizeof(int), len);
for(i = 0; i < len; i++)
{
stack->push(stack, &data[i]);
}
for (i = 0; i < len; i++)
{
TEST_ASSERT_TRUE(stack->peek(stack, &temp));
TEST_ASSERT_EQUAL_INT(data[stack->size(stack) - 1], temp);
TEST_ASSERT_TRUE(stack->pop(stack, &temp));
if (!stack->empty(stack))
{
TEST_ASSERT_TRUE(stack->peek(stack, &temp));
TEST_ASSERT_EQUAL_INT(data[stack->size(stack) - 1], temp);
}
else
{
TEST_ASSERT_FALSE(stack->peek(stack, &temp));
}
}
TEST_ASSERT_TRUE(stack->empty(stack));
TEST_ASSERT_FALSE(stack->pop(stack, &temp));
stack_free(&stack);
// ------------------------------
// if capacity is less than data len
stack = stack_new();
stack_init2(stack, sizeof(int), len - 2);
for(i = 0; i < len; i++)
{
TEST_ASSERT_TRUE(stack->push(stack, &data[i]));
TEST_ASSERT_EQUAL_INT(i + 1, stack->size(stack));
}
uint32_t capacity = stack->capacity(stack);
for (i = 0; i < len; i++)
{
if (!stack->empty(stack))
{
TEST_ASSERT_TRUE(stack->pop(stack, &temp));
}
else
{
TEST_ASSERT_FALSE(stack->pop(stack, &temp));
}
if (!stack->empty(stack))
{
TEST_ASSERT_TRUE(stack->peek(stack, &temp));
TEST_ASSERT_EQUAL_INT(data[stack->size(stack) - 1], temp);
}
else
{
TEST_ASSERT_FALSE(stack->pop(stack, &temp));
TEST_ASSERT_FALSE(stack->peek(stack, &temp));
}
}
stack_free(&stack);
}
static void test_stack_clear(void)
{
int temp = 0;
int data[] = { 1,2,3,4,5,6,7,8,9,10 };
uint32_t len = sizeof(data) / sizeof(data[0]);
uint32_t i = 0;
stack_t stack = NULL;
// ------------------------------
stack = stack_new();
stack_init(stack, sizeof(int));
for(i = 0; i < len; i++)
{
stack->push(stack, &data[i]);
}
TEST_ASSERT_TRUE(stack->clear(stack));
for(i = 0; i < len; i++)
{
stack->push(stack, &data[i]);
}
TEST_ASSERT_FALSE(stack->empty(stack));
TEST_ASSERT_TRUE(stack->clear(stack));
TEST_ASSERT_TRUE(stack->empty(stack));
TEST_ASSERT_TRUE(stack->clear(stack));
stack_free(&stack);
// ------------------------------
stack = stack_new();
stack_init2(stack, sizeof(int), len);
TEST_ASSERT_TRUE(stack->clear(stack));
for(i = 0; i < len; i++)
{
stack->push(stack, &data[i]);
}
TEST_ASSERT_FALSE(stack->empty(stack));
TEST_ASSERT_TRUE(stack->clear(stack));
TEST_ASSERT_TRUE(stack->empty(stack));
TEST_ASSERT_TRUE(stack->clear(stack));
stack_free(&stack);
}
static void test_stack_num(void) static void test_stack_num(void)
{ {
uint32_t i = 0; uint32_t i = 0;
@ -46,7 +297,35 @@ static void test_stack_num(void)
TEST_ASSERT_NULL(stack); TEST_ASSERT_NULL(stack);
} }
static void test_stack_struct(void)
{
}
static void test_stack2_num(void)
{
}
static void test_stack2_struct(void)
{
}
void test_stack(void) void test_stack(void)
{ {
RUN_TEST(test_stack_num); RUN_TEST(test_stack_num);
RUN_TEST(test_stack_init);
RUN_TEST(test_stack_new);
RUN_TEST(test_stack_push);
RUN_TEST(test_stack_pop);
RUN_TEST(test_stack_clear);
RUN_TEST(test_stack_num);
RUN_TEST(test_stack_struct);
RUN_TEST(test_stack2_num);
RUN_TEST(test_stack2_struct);
} }