3

我是 C 的新手,我正在尝试实现一个链表,其中节点定义如下:

typedef struct _cListNode
{
    void *_data;                //generic pointer to any data type
    struct _cListNode *next;    //next node in the list
} cListNode;

我需要 InsertElement(cList myList, void *dataToInsert) 函数在插入的元素已经存在(即没有重复)时不增加列表。我目前的问题是我找不到将dataToInsert(参数)与 _ data(在我的节点内)进行比较的方法。

我想在调用 InsertElement 函数之前在外部遍历列表,并在我知道类型是什么但我希望有更好的设计/解决方案的列表实现之外处理比较。

4

2 回答 2

4

给定两个 void 指针,无法比较它们的数据。这是因为您不知道每个指针的类型的大小。如果要比较它们的数据,则需要存储指针及其数据的大小。然后你可以使用 memcmp 来比较指向的内存:

 typedef struct _cListNode
 {
     void *_data;                //generic pointer to any data type
     size_t size;
     struct _cListNode *next;    //next node in the list
 } cListNode;

 int memcmp ( const void * ptr1, const void * ptr2, size_t num );

所以:

 memcmp(node_data_ptr, new_data_ptr, size_of_item_pointed_at);

如果两个指针的大小相同,则只应执行 memcmp,否则它们明显不同,并且您不想最终比较无效内存。

您的另一个选择是比较指针本身并查看它们是否指向同一段内存。这取决于您所说的“重复”是什么意思。

于 2013-01-18T15:51:28.273 回答
2

你可能想做这样的事情。我假设您的链表结构如下:

typedef struct _cList
{
   cListNode* head;
   cListNode* tail;
   size_t size;
} cList;

int contains(cList* list, void* data, size_t dataSize)
{
   cListNode* temp = list->head;

   while(temp)
   {
      if(!memcmp(data, temp->_data, dataSize))
         return 1;
      temp = temp->next;
   }
   return 0;
}


void InsertElement(cList* myList, void *dataToInsert, size_t dataSize)
{
   if(!contains(myList,dataToInsert, dataSize))
   {
     //Insert Data
   }
   else
   {
     //Data Is already present.
   }
}

您应该struct cListNode按照@jmh 的答案中指定的方式创建。

于 2013-01-18T16:10:34.237 回答