链表与复数运算:深入解析与优化
在计算机科学中,链表是一种常见的数据结构,它通过指针将一组节点连接起来。每个节点包含两部分:数据和指向下一个节点的指针。在本篇文章中,我们将通过一个具体的 C 语言程序,来详细了解如何创建一个复数链表,并计算所有复数的和。
题目描述
从键盘读入n个复数(实部和虚部都为整数)用链表存储,遍历链表求出n个复数的和并输出。
输入格式
无
输出格式
无
样例输入
3 3 4 5 2 1 3
样例输出
9+9i
一、代码概述
这段代码的主要功能是创建一个复数链表,并计算链表中所有复数的和。代码分为以下几个部分:
链表的创建:根据用户输入的复数数量,创建一个复数链表。
计算复数和:遍历链表,计算所有复数的实部和虚部之和。
内存管理:释放链表占用的内存,避免内存泄漏。
二、代码分析
1. 复数链表的创建
c复制
Node *create(int n)
{
Node *head, *p, *q;
head = (Node *)malloc(sizeof(Node)); // 创建头节点
if (n == 0)
{
head->next = NULL;
return head;
}
else
{
p = head;
for (int i = 0; i < n; i++)
{
q = (Node *)malloc(sizeof(Node)); // 创建新节点
scanf("%d%d", &q->real, &q->imag); // 输入实部和虚部
q->next = NULL;
p->next = q;
p = q;
}
}
return head;
}
功能:根据用户输入的复数数量
n
,创建一个链表。关键点:
使用头节点(
head
),它本身不存储数据,但方便后续操作。使用指针
p
和q
来动态扩展链表。通过
malloc
动态分配内存来创建新节点。如果
n
为 0,链表为空。
2. 计算复数和
c复制
Node *sumNode(Node *head)
{
Node *p;
p = head->next; // 跳过头节点
if (p == NULL)
{
printf("0+0i\n");
return head;
}
else
{
Node *newNode = (Node *)malloc(sizeof(Node)); // 创建新节点存储结果
newNode->next = NULL;
newNode->real = 0;
newNode->imag = 0;
while (p != NULL)
{
newNode->real += p->real; // 实部累加
newNode->imag += p->imag; // 虚部累加
p = p->next;
}
free(head); // 释放头节点
printf("%d+%di\n", newNode->real, newNode->imag);
return newNode;
}
}
功能:遍历链表,计算所有复数的实部和虚部之和,并输出结果。
关键点:
使用头节点的下一个节点作为链表的起始点。
创建一个新节点
newNode
来存储复数和。实部和虚部分别累加。
输出结果格式为
a+bi
。释放头节点,避免内存泄漏。
3. 主函数
c复制
int main(void)
{
int n;
Node *head;
scanf("%d", &n); // 输入复数数量
head = create(n); // 创建链表
head = sumNode(head); // 计算复数和
return 0;
}
功能:整合链表的创建和复数和的计算。
关键点:
用户输入复数数量
n
。调用
create
函数创建链表。调用
sumNode
函数计算复数和。
三、代码优化
1. 链表打印功能
c复制
void print_link(Node *head)
{
Node *p;
p = head->next; // 跳过头节点
if (p == NULL)
printf("链表为空!\n");
else
{
printf("链表中的复数为:");
while (p != NULL)
{
printf("(%d+%di)", p->real, p->imag);
p = p->next;
}
printf("\n");
}
}
功能:打印链表中的每一个复数。
2. 内存释放功能
c复制
void free_link(Node *head)
{
Node *p, *q;
p = head;
while (p != NULL)
{
q = p->next;
free(p);
p = q;
}
}
功能:释放链表占用的内存。
3. 改进后的主函数
c复制
int main(void)
{
int n;
Node *head;
scanf("%d", &n); // 输入复数数量
head = create(n); // 创建链表
print_link(head); // 打印链表
head = sumNode(head); // 计算复数和
free_link(head); // 释放链表内存
return 0;
}
功能:在计算复数和之前,打印链表内容,并在程序结束时释放链表内存。
四、运行示例
假设用户输入如下数据:
复制
请输入复数数量:3
1 2 // 第一个复数:1+2i
3 4 // 第二个复数:3+4i
5 6 // 第三个复数:5+6i
程序输出:
复制
链表中的复数为:(1+2i)(3+4i)(5+6i)
复数和为:9+12i
五、总结
通过这段代码,我们不仅实现了复数链表的创建和复数和的计算,还添加了链表打印和内存释放功能。链表作为一种动态数据结构,具有灵活的内存分配和高效的插入删除操作。在实际应用中,链表可以用于实现各种数据结构,如复数计算、多项式处理等。
希望这篇文章能帮助你更好地理解链表的基本操作和复数处理。如果你对链表的其他操作感兴趣,比如插入、删除节点等,欢迎继续探索!
源代码
#include <stdio.h>
#include <stdlib.h>
typedef struct Node
{
int real;
int imag;
struct Node *next;
}Node;
Node *create (int n)
{
Node *head,*p,*q;
head = (Node *)malloc (sizeof(Node));
if(n == 0)
{
head->next =NULL;
return head;
}
else
{
p = head;
for(int i =0; i<n;i++)
{
q = (Node *)malloc(sizeof(Node));
scanf("%d%d",&q->real,&q->imag);
q->next = NULL;
p->next = q;
p = q;
}
}
return head;
}
//计算所有复数的值
Node *sumNode(Node *head)
{
Node *p;
p = head->next;
if(p == NULL)
{
printf("0+0i\n");
return head;
}
else
{
Node *newNode = (Node *)malloc(sizeof(Node));
newNode->next = NULL;
newNode->real = 0;
newNode->imag = 0;
while (p != NULL)
{
newNode->real += p->real;
newNode->imag += p->imag;
p = p->next;
}
free(head);
printf("%d+%di\n",newNode->real,newNode->imag);
return newNode;
}
}
int main(void)
{
int n;
Node *head;
scanf("%d",&n);
head = create(n);
head = sumNode(head);
return 0;
}