【求助】用链表实现堆栈和队列时的迷惑

guocai_yao 2009-04-10 09:30:15
先看一个程序:有问题的地方的是pop函数:

#include <stdio.h>
#include <stdlib.h>
#include <conio.h>
#include <malloc.h>

#define ELEM_TYPE int

typedef struct NODE{
ELEM_TYPE data;
struct NODE *next;
}linked_stack;

#define LEN (sizeof(linked_stack))

linked_stack *linked_stack_init(void)
{
linked_stack *top ;
top = NULL;
return top;
}

int linked_stack_is_empty(linked_stack *top)
{
return (top == NULL);
}

linked_stack *linked_stack_push(linked_stack *top, ELEM_TYPE x)
{
linked_stack *new = (linked_stack *)malloc(LEN);
if(new == NULL){
printf("Allocate memory error!\n");
exit(EXIT_FAILURE);
}
new->data = x;
new->next = top;
top = new;

return top;
}

int linked_stack_pop(linked_stack *top)
{
ELEM_TYPE x;
linked_stack *tmp = top;

if(linked_stack_is_empty(top)){
printf("Empty!\n");
exit(EXIT_FAILURE);
}
x = top->data;
top = top->next;
free(tmp);
return x;
}

ELEM_TYPE linked_stack_get_top(linked_stack *top)
{
if(linked_stack_is_empty(top)){
printf("Empty!\n");
exit(EXIT_FAILURE);
}
return top->data;
}

int main()
{
int x;
linked_stack *s = linked_stack_init();

s = linked_stack_push(s, -23);
s = linked_stack_push(s, 44);
s = linked_stack_push(s, 1);
x = linked_stack_pop(s);
printf("%d ", x);
x = linked_stack_pop(s);
printf("%d ", x);
x = linked_stack_pop(s);
printf("%d ", x);

return 0;
}

再看一个程序,注意linked_queue_out函数

#include <stdio.h>
#include <stdlib.h>
#include <conio.h>
#include <malloc.h>
#include <assert.h>

#define ELEM_TYPE int

typedef struct NODE{
ELEM_TYPE data;
struct NODE *next;
}linked_queue_node;

typedef struct HEAD_TAIL{
linked_queue_node *front;
linked_queue_node *rear;
}linked_queue;

#define LEN_NODE (sizeof(linked_queue_node))
#define LEN_HEAD_TAIL (sizeof(linked_queue))

linked_queue *linked_queue_init(void)
{
linked_queue_node *p = NULL;
/*申请头尾指针节点*/
linked_queue *Q = (linked_queue *)malloc(LEN_HEAD_TAIL);
if(NULL == Q){
printf("Allocate memory error!\n");
exit(EXIT_FAILURE);
}
/*申请链队头节点*/
p = (linked_queue_node *)malloc(LEN_NODE);
if(NULL == p){
printf("Allocate memory error!\n");
exit(EXIT_FAILURE);
}
p->next = NULL;/*头结点的指针域为空*/
Q->rear = Q->front = p;
return Q;
}

int linked_queue_is_empty(linked_queue *Q)
{
return (Q->front->next == NULL);
}

void linked_queue_in(linked_queue *Q, ELEM_TYPE x)
{
linked_queue_node *new = (linked_queue_node *)malloc(LEN_NODE);
if(new == NULL){
printf("Allocate memory error!\n");
exit(EXIT_FAILURE);
}
assert(x != -1);/*-1只作为队列为空时的标志*/
new->data = x;
/*FIFO,插入链表的尾部*/
new->next = NULL;
Q->rear->next = new;
Q->rear = new;
}

ELEM_TYPE linked_queue_out(linked_queue *Q)
{
ELEM_TYPE x;
linked_queue_node *tmp;
if(linked_queue_is_empty(Q)){
printf("Empty\n");
return -1; /*空队列返回数值-1*/
}
tmp = Q->front->next;/*保存第一个节点*/
x = tmp->data;
Q->front->next = tmp->next;
free(tmp);
/*出队后链表若为空,调整队列尾指针*/
if(linked_queue_is_empty(Q))
Q->rear = Q->front;
return x;
}

void linked_queue_print(const linked_queue *Q)
{
linked_queue_node *p = Q->front->next;/*头结点Q->front->next不打印*/
if(p == NULL){
printf("Empty\n");
return;
}
while(p != NULL){
printf("%d ", p->data);
p = p->next;
}
printf("\n");
}

int main()
{
ELEM_TYPE x;
linked_queue *q = linked_queue_init();
linked_queue_in(q, 30);
linked_queue_in(q, 10);
printf("After in, the queue is: ");
linked_queue_print(q);

x = linked_queue_out(q);
printf("the value come out the queue is %d \n", x);
printf("After out, the queue is: ");
linked_queue_print(q);

x = linked_queue_out(q);
printf("the value come out the queue is %d \n", x);
printf("After out, the queue is: ");
linked_queue_print(q);

return 0;
}

linked_stack_pop函数和linked_queue_out函数同样是对传过来的指针的副本进行修改,为什么一个成功一个失败?
感觉自己对指针的理解还是不透彻啊!
...全文
138 7 打赏 收藏 转发到动态 举报
AI 作业
写回复
用AI写文章
7 条回复
切换为时间正序
请发表友善的回复…
发表回复
  • 打赏
  • 举报
回复
linked_stack_pop函数和linked_queue_out函数同样是对传过来的指针的副本进行修改,为什么一个成功一个失败?


你都知道是传指针的副本,那如果你的函数需要修改的是指针本题,就会出问题撒.
ylywyn136 2009-04-10
  • 打赏
  • 举报
回复
top = top->next;你的这个有问题
zhanghuayi_xiyou 2009-04-10
  • 打赏
  • 举报
回复
当然不对了,linked_queue_out只是改变了头指针的副本,而没有改变主函数变量s 。
而linked_queue_out参数是linked_queue *Q,没有改变Q的副本,但改变主函数(*q).front的值,


给你的建议,linked_queue_out的参数使用二级指针。这样主函数变量s 就能改变。
zhanghuayi_xiyou 2009-04-10
  • 打赏
  • 举报
回复
当然不对了,linked_queue_out只是改变了头指针的副本,而没有改变主函数变量s 。
而linked_queue_out参数是linked_queue *Q,没有改变Q的副本,但改变主函数(*q).front的值,


给你的建议,linked_queue_out的参数使用二级指针。这样主函数变量s 就能改变。
guocai_yao 2009-04-10
  • 打赏
  • 举报
回复
[Quote=引用 2 楼 zhanghuayi_xiyou 的回复:]
当然不对了,linked_queue_out只是改变了头指针的副本,而没有改变主函数变量s 。
而linked_queue_out参数是linked_queue *Q,没有改变Q的副本,但改变主函数(*q).front的值,


给你的建议,linked_queue_out的参数使用二级指针。这样主函数变量s 就能改变。
[/Quote]
linked_queue_out可以实现功能 linked_stack_pop出问题; 但是两个函数都是修改的是指针的的副本 所以都不可以这样用的 想知道linked_queue_out是否是碰巧成功的?
guocai_yao 2009-04-10
  • 打赏
  • 举报
回复
[Quote=引用 4 楼 hairetz 的回复:]
linked_stack_pop函数和linked_queue_out函数同样是对传过来的指针的副本进行修改,为什么一个成功一个失败?


你都知道是传指针的副本,那如果你的函数需要修改的是指针本题,就会出问题撒.
[/Quote]
其实想知道 linked_queue_out是怎么成功的?
guocai_yao 2009-04-10
  • 打赏
  • 举报
回复
[Quote=引用 3 楼 ylywyn136 的回复:]
top = top->next;你的这个有问题
[/Quote]
什么问题?
内容概要:本文介绍了软件定义汽车(SDV)的最佳实践案例,重点围绕基于Vector技术的电子电气(E/E)架构设计与实现。文档展示了高算力计算平台(HPC)、区域控制器(Zone ECU)和车载网络(如CAN、Ethernet)的系统架构布局,并结合AUTOSAR操作系统(Classic/Adaptive)、虚拟化(Hypervisor)和SOA服务设计,构建现代化车载系统。通过vCANdrive平台演示了从开发、测试(SIL/HIL)、到OTA升级的全流程,涵盖传感器、执行器、应用层软件及云端协同的集成方案。同展示了硬件原型(如树莓派、Triboard)和MICROSAR系列工具链在实际项目中的应用。; 适合人群:从事汽车电子系统开发、车载软件架构设计以及智能网联汽车研发的工程师和技术管理人员,具备一定的嵌入式系统或AUTOSAR基础者更佳。; 使用场景及目标:①理解软件定义汽车的整体架构设计方法;②掌握基于Vector工具链的HPC与区域控制器集成方案;③实现OTA更新、SIL/HIL测试、ETH-CAN通信转换等关键技术验证;④支持智能驾驶(ADAS)与智能座舱(IVI)系统的快速原型开发。; 阅读建议:建议结合Vector相关工具(如PREEvision、CANoe4SW、MICROSAR)进行实践操作,重点关注系统分层设计、通信机制与软件更新流程,同可参考文档中的硬件连接示意图与信号映射关系进行仿真与实车验证。

70,026

社区成员

发帖
与我相关
我的任务
社区描述
C语言相关问题讨论
社区管理员
  • C语言
  • 花神庙码农
  • 架构师李肯
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧