我正在学习数据结构。所以我决定自己用数组实现一个栈。问题是当程序试图在栈满的时候推送一个元素。我的想法是realloc()指向数组的现有指针,我以前用malloc手动分配内存()将堆栈的大小增加1,然后推送相应的Item。在valgrind上运行代码后,它向我显示错误:“大小为4的无效写入...在大小为16的块分配之前有4个字节“。注意到我是初学者,因此感谢任何帮助。
typedef struct {
int *v;
int cap;
int sz;
} stack;
stack* build(){
stack *new = (stack*) malloc(sizeof(stack));
new->v = (int*) malloc(sizeof(int) * 4);
new->cap = 4;
new->sz = 0;
return new;
}
int is_empty(stack *s){
return s->sz == 0;
}
int push( stack *s, int e )
{
int success = 1;
if (s->sz == s->cap){
int*tmp =(int*)realloc(s->v,(s->cap+1)*sizeof( int));
if (( success = tmp != NULL )){
s->v = tmp;
++s->cap;
}
}
if (success){
s->v[s->sz++] = e;
}
return success;
}
int top(stack *s){
return *(s->v);
}
int pop(stack *s){
int value;
if(is_empty(s))
return -1;
value = *(s->v);
s->v--;
s->sz--;
return value;
}
void destroy(stack *s){
s->v -= s->sz + 1;
free(s->v);
free(s);
}
int match(char p1, char p2){
if(p1 == '(')
return (p1 - p2) == '(' - ')';
else if(p1 == '[')
return (p1 - p2) == '[' - ']';
else
return (p1 - p2) == '{' - '}';
}
int main(){
int c;
stack *s = build();
while((c = getchar()) != EOF && c != '\n'){
if(c == '(' || c == '[' || c == '{')
push(s, c);
else if(c == ')' || c == ']' || c == '}'){
if(!match(pop(s), c)){
printf("no\n");
destroy(s);
return 0;
}
}
}
puts((is_empty(s)) ? "yes" : "no");
destroy(s);
return 0;
}
1条答案
按热度按时间pinkon5k1#
realloc
的调用不正确。函数的第一个参数应该是指向先前分配的内存的原始指针或NULL。
此外,在函数
push
中进行此检查是多余的。
函数可以看起来像下面这样。注意函数不应该发出任何消息。它是函数的调用者,将根据新项是否成功添加来决定是否输出消息。
下面是一个演示程序,展示了函数
push
的用法。程序输出为
当然,你需要自己写一个函数来释放所有分配的内存。
请注意,最好将堆栈定义为单链表。