毕业之前实现过的,当时受到老师一点好评,有所印象,暂未发现完全相近实现,分享出来
另外递归实现可以通过栈间接省去变量,也是个代码简洁但使用有限的算法,有限之处在于链表过长会栈异常,效率也不好。
#include <stdio.h>
#include <stdlib.h>
struct node_t
{
int val;
struct node_t* prev;
struct node_t* next;
};
inline void dump_list(node_t* p)
{
while(p)
{
printf("%d ", p->val);
p = p->next;
}
printf("\n");
}
//单链表逆序,改进不存3个变量,先预处理一个节点
node_t* reverse_list(node_t* p)
{
if(p == NULL || p->next == NULL)
return p;
node_t* head = p, *p1; //head为新链表首节点
p = p->next; //优先首节点处理为尾节点
head->next = NULL;
while(p)
{
p1 = p; //向下偏移
p = p->next;
p1->next = head; //链表至head
head = p1;
}
return head;
}
//双链表逆序,直接颠倒prev和next
node_t* reverse_dlist(node_t* p)
{
if(p == NULL || p->next == NULL)
return p;
node_t* head = p, *p1, *tmp; //head指向第一个节点
while(p)
{
p1 = p; //向下偏移
p = p->next;
tmp = p1->next; //prev和next交换
p1->next = p1->prev;
p1->prev = tmp;
}
p1->prev = head->next; //首节点prev恢复
head->next = NULL; //尾节点next终止
return p1;
}
int main(int agc, char* argv[])
{
node_t node = {0, NULL};
node_t* p = &node; //哨兵节点
int val;
while(scanf("%d", &val) == 1)
{
node_t* node = (node_t*)malloc(sizeof(node_t));
node->val = val;
node->next = NULL;
node->prev = p;
p->next = node;
p = node;
}
dump_list(node.next);
node.next = reverse_dlist(node.next); //测试,一定要双链表在先,因为单链表逆序会破坏双链表结构
node.next = reverse_dlist(node.next);
node.next = reverse_dlist(node.next);
node.next = reverse_list(node.next);
node.next = reverse_list(node.next);
node.next = reverse_list(node.next);
node.next = reverse_list(node.next);
dump_list(node.next);
return 0;
}