集合交差并三种操作的C实现
首先说明一下集合的ADT,肯定有包括基本的创建、删除操作。以及某一个元素的插入和删除操作。集合的一个重要特征就是元素的不重复性。这种方式我在实现的过程中通过链表管理一个集合,按照元素的大小进行排列,之所以排列主要是为了方便删除、查找元素的操作。实质上集合对元素的顺序是没有要求的。
集合的交集:是指两个集合元素相同的部分构成的集合。
集合的差集:是指其中一个集合中除去另一个集合相同元素以后剩余的元素构成的集合。
集合的并集:是指两个集合的所有元素构成的集合。
其中需要注意的就是集合的元素是不能重复的,本来我打算采用二叉查找树的方式实现,因为这种树型结构便于快速的查询,但是我采用元素的升序排序就能避免集合中漫无目的的查询操作。毕竟实现二叉查找树也增加了一个指针成员,而且还需要大量的操作。
简要的说明一下我的过程:
基本的集合结构体:
typedef struct linknode
{
struct linknode *next;
int value;
}Node_t, *Node_handle_t;
typedef struct set
{
unsigned int size;
Node_handle_t head;
}Set;
集合的创建,该函数的实现是集合实现的最复杂的一个函数,之所以这么复杂是因为很多的操作都是基于该函数完成的,当然也可以采用更精细的函数来实现,我开始的想法是将元素插入和创建操作合并,都基于一个函数进行操作,但是写完以后发现函数太长,而且比较烂,不够必将还是完成了一些基本的操作。采用了升序存储的方式,主要是为了后续的查找操作,注意链表的更新操作。
bool create_set(Set **sets, int data)
{
Set * temp = (Set *)malloc(sizeof(Set)/sizeof(char));
Node_t *node = NULL;
Node_t *head = NULL;
if(*sets == NULL)
{
temp->size = 0;
temp->head = NULL;
*sets = temp;
node = (Node_t *)malloc(sizeof(Node_t)/sizeof(char));
if(node != NULL)
{
node->next = NULL;
node->value = data;
/*更新集合指针*/
temp->head = node;
temp->size ++;
*sets = temp;
temp = NULL;
return true;
}
}
else/*已经存在部分集合*/
{
/******************************
采用顺序存储的方式插入新的元素
首先查找是否存在值,有不做任何操作
不存在,则按值大小找到合适的位置
******************************/
/*遍历*/
if((*sets)->head != NULL)
{
/*更新表头*/
if((*sets)->head->value > data)
{
node = (Node_t *)malloc(sizeof(Node_t)/sizeof(char));
if(node == NULL)
return false;
node->next = (*sets)->head;
node->value = data;
(*sets)->head = node;
(*sets)->size ++;
return true;
}
else if((*sets)->head->value == data)
{
return true;
}
/*从下一个节点开始*/
head = (*sets)->head;
node = head;
while(head->next != NULL)
{
/*已经存在*/
if(head->next->value == data)
{
return true;
}
/*找到合适的位置,并插入*/
else if(head->next->value > data)
{
node = (Node_t *)malloc(sizeof(Node_t)/sizeof(char));
if(node == NULL)
return false;
node->value = data;
node->next = head->next;
head->next = node;
(*sets)->size ++;
return true;
}
else
{
head = head->next;
}
}
/*说明以上不存在该值*/
node = (Node_t *)malloc(sizeof(Node_t)/sizeof(char));
if(node == NULL)
return false;
node->value = data;
node->next = NULL;
head->next = node;
(*sets)->size ++;
return true;
}
else
{
node = (Node_t *)malloc(sizeof(Node_t)/sizeof(char));
if(node == NULL)
return false;
node->value = data;
node->next = NULL;
(*sets)->head = node;
(*sets)->size ++;
return true;
}
}
return false;
}
查找、删除元素操作,充分利用了前面的升序存储关系。
评论