我有一个通用的链表,其中保存的数据类型为空*我试图填充我的列表与结构雇员类型,最终我想破坏对象结构雇员以及。
考虑这个通用的链接列表头文件(我已经用char*类型测试过了):
struct accListNode //the nodes of a linked-list for any data type
{
void *data; //generic pointer to any data type
struct accListNode *next; //the next node in the list
};
struct accList //a linked-list consisting of accListNodes
{
struct accListNode *head;
struct accListNode *tail;
int size;
};
void accList_allocate(struct accList *theList); //allocate the accList and set to NULL
void appendToEnd(void *data, struct accList *theList); //append data to the end of the accList
void removeData(void *data, struct accList *theList); //removes data from accList
--------------------------------------------------------------------------------------
考虑员工结构
struct employee
{
char name[20];
float wageRate;
}
现在考虑从main()调用的示例测试用例:
void test2()
{
struct accList secondList;
struct employee *emp = Malloc(sizeof(struct employee));
emp->name = "Dan";
emp->wageRate =.5;
struct employee *emp2 = Malloc(sizeof(struct employee));
emp2->name = "Stan";
emp2->wageRate = .3;
accList_allocate(&secondList);
appendToEnd(emp, &secondList);
appendToEnd(emp2, &secondList);
printf("Employee: %s\n", ((struct employee*)secondList.head->data)->name); //cast to type struct employee
printf("Employee2: %s\n", ((struct employee*)secondList.tail->data)->name);
}
为什么我在下面发布的答案解决了我的问题?我相信这与指针和内存分配有关。我使用的函数Malloc()是一个自定义Malloc,用于检查是否返回NULL。
下面是我的整个通用链表实现的链接:https://codereview.stackexchange.com/questions/13007/c-linked-list-implementation
在上面的问题中,根据原始代码,我认为有两件事是错误的,
您所看到的是未定义的行为,并由此产生的是总线错误消息,因为您正在为变量分配字符串文本,而实际上您应该使用strcpy
函数,因此您已经相应地编辑了原始代码。
使用Malloc
这个词会引起混乱,尤其是在同行评议中,评论者会有一个大脑屁,然后说“哇,这是什么,这不应该是Malloc吗?”而且很可能会把它抬高。(基本上,不要调用与C标准库函数名称相似的自定义函数)
您没有检查NULL
,如果您的增强版Malloc
失败了,那么emp
将是NULL
!无论多么琐碎或您的想法是“啊,她的平台上有大量内存,4GB内存没问题,不会费心检查为NULL”,请始终检查它
看看其他地方发布的这个问题,来解释什么是总线错误。
编辑:使用链表结构,如何调用函数中的参数对理解函数至关重要。注意
在问题的第一个代码中,参数有点不合适,如果在参数列表中使用双指针,那么是的,使用
我认为你的问题是:
test2
函数的堆栈上分配了第二个列表
。秒列表
需要初始化accList_allocate
函数获取指向列表的指针,但随后用Malloc
调用覆盖它。这意味着您传入的指针永远不会初始化。test2
尝试运行时,它会碰到一个错误的指针(因为内存没有初始化)。当您在main
中分配它时,它起作用的原因是当程序启动时,您的C编译器可能会将堆栈归零。当main
在堆栈上分配变量时,这种分配是持久的(直到程序结束),所以当您在main
中分配它时,第二列表
实际上是意外地正确初始化的。
您当前的accList_allocate
实际上并没有初始化传入的指针,代码的其余部分将永远看不到它分配给Malloc
的指针。为了解决您的问题,我将创建一个新函数:accList_initialize
,它的唯一工作是初始化列表:
void accList_initialize(struct accList* theList)
{
// NO malloc
theList->head = NULL;
theList->tail = NULL;
theList->size = 0;
}
在原来的test2
函数中,使用这个函数,而不是accList\u allocate
。如果你真的想在堆上分配列表,那么你应该这样做(不要把它和在堆栈上分配的结构混在一起)。让accList\u allocate
返回一个指向已分配结构的指针:
struct accList* accList_allocate(void)
{
struct accList* theList = Malloc( sizeof(struct accList) );
accList_initialize(theList);
return theList;
}
问题在于accList_allocate()和您对它的使用。
struct accList secondList;
accList_allocate(&secondList);
在最初的test2()中,第二个列表是堆栈上的内存。
返回后,secondList仍然指向堆栈上未初始化的内存,因此对appendToEnd()的调用失败。
同样的事情也会发生在答案上,除了第二个列表恰好没有垃圾。可能是偶然的,也可能是编译器的设计。不管怎样,它都不是你应该依赖的东西。
要么:
struct accList *secondList = NULL;
accList_allocate(&secondList);
并更改accList_allocate()
accList_allocate(struct accList **theList) {
*theList = Malloc(sizeof(struct accList));
(*theList)->head = NULL;
(*theList)->tail = NULL;
(*theList)->size = 0;
}
或
struct accList secondList;
accList_initialise(secondList);
accList_allocate()改为accList_initialise(),因为它不分配
accList_initialise(struct accList *theList) {
theList->head = NULL;
theList->tail = NULL;
theList->size = 0;
}
本文向大家介绍C#通过链表实现队列的方法,包括了C#通过链表实现队列的方法的使用技巧和注意事项,需要的朋友参考一下 本文实例讲述了C#通过链表实现队列的方法。分享给大家供大家参考。具体实现方法如下: 希望本文所述对大家的C#程序设计有所帮助。
嘿,伙计们,我在让for循环工作时遇到了一些麻烦。myList是一个链表,其中填充了文件中的数字,我正在尝试遍历它并以一种(当前,下一个)的方式打印当前值和每个下一个值- 出于某种原因,for循环无法执行任何操作,或者更确切地说,代码在for循环的开始就中断了。如果我摆脱for循环并只是复制和粘贴 很多时候它会按照我的意愿工作,但我宁愿不这样做。for 循环语法看起来是正确的,如果 say cou
在试图理解如何在C#中实现单个列表时,我遇到了下面的链接: 创建一个非常简单的链表。 然而,由于我是C#的新手,我被上面讨论的第一部分中列出的语法弄糊涂了。正在声明一个名为节点的类,并且在声明为“公共节点下一个”的类中还有另一个语句。这个语句称为构造函数吗?请帮忙。
所以我有一个堆栈,它允许典型的Push和Pop函数。我很难理解这一切实际上是如何在代码方面工作的。我在这里看到了这篇文章,最佳答案中的图片/图表,展示了列表是如何被“推”下来的,你指向最新的元素。我有一个 它挂接到结构“节点” 我如何结合一个推拉与"节点*下一步;"?最难理解的是我将如何真正做到这一点。我知道它最初指向空,然后如果我推一个2,4,6,它将是6,4,2,#。掌握如何实际使用链表中的指
众所周知,iOS深层链接已经改变了一点,称为通用链接,有了通用链接,我们需要在您的Xcode项目中启用“关联域”,并在那里添加受支持的域,还有一些变化,如在域服务器上托管苹果应用站点关联JSON。 这一点我非常理解,但我的问题是我必须支持多个社区,可能每个使用应用程序的企业都会有自己的社区,所以将所有社区(域)添加到“关联域”中不是一件好事,如果有新企业使用应用程序,然后我需要提供一个应用程序更新
1.1.1. 目录 1.1.2. 一、概述 1.1.3. 二、硬件示例 1.1.4. 三、软件架构 1.1.5. 四、全链路集成 1.1.6. 五、API参考 1.1.1. 目录 一、概述 Rokid全链路通用方案 软件框架简介 二、硬件示例 三、软件架构 SDK目录结构 config doc executable android-libraries文件列表 shared-libraries文件列