c语言大数相加 和小于,大数相加

该楼层疑似违规已被系统折叠 隐藏此楼查看此楼

#include

#include

/**

*

* 定义双向节点

* 数据区为一个整型数字

*

**/

struct Node {

int number;//数据区,仅一个数字,保存一位数字

struct Node * next;

struct Node * prev;

};

typedef struct Node Node;

/**

* 创建头节点

* param:number,此数字赋值给创建出的节点的数字区

* return:创建出来的头结点

*

*

**/

Node * create_head(int number){

Node * head = (Node *)malloc(sizeof(Node));

head->number = number;

//只有一个节点的时候,此节点的next和prev均为NULL

head->next = NULL;

head->prev = NULL;

return head;

}

/**

* 创建一个新的节点,并将此节点追加到链表的最末端

* param:**tail链表尾指针的指针,因为方法中需要修改尾指针,因为你懂的原因,这里使用了指针的指针

* number整型数字,赋值给新节点的数据区

**/

void create_node_to_tail(Node ** tail,int number){

//为新节点开辟空间

Node * node = (Node *)malloc(sizeof(Node));

node->number = number;

//因为新节点要加到尾部,所以它的next变为NULL,prev指向原有的尾部

node->next = NULL;

node->prev = *tail;

//原有的尾部的next指向最新的节点

(*tail)->next = node;

//新节点到链表尾部之后,新节点成为链表的尾部

*tail = node;

}

/**

* 创建一个新的节点,并将此节点追加到链表的最前端

* param**head链表头指针的指针,原因同上

* number同上

*

**/

void create_node_to_head(Node ** head,int number){

//为新节点开辟空间

Node * node = (Node *)malloc(sizeof(Node));

node->number = number;

//新节点加到头前面,所以它的prev变为NULL,next指向原有的头部

node->prev = NULL;

node->next = *head;

//原有的头部的prev指向最新的节点

(*head)->prev = node;

//最新的节点成为新的头部

*head = node;

}

/**

* 大数相加

* param:number1_head加数1的头指针

* number2_head加数2的头指针

* return:计算结果的尾指针,主要是为了方便输出

*

**/

Node * add_big(Node * number1_head,Node * number2_head){

//进位

int carry = 0;

Node * number1_current = number1_head;

Node * number2_current = number2_head;

//保存计算结果的链表的头指针和尾指针

Node * result_head = NULL;

Node * result_tail = NULL;

//循环时,只要有一个加数没有结束,则继续循环

while(number1_current != NULL || number2_current != NULL){

//加数1,如果节点为NULL,则此加数为0,应对两个加数不一样长的情况

int number1 = (number1_current == NULL)?0:number1_current->number;

//加数2,如果节点为NULL,则此加数为0,应对两个加数不一样长的情况

int number2 = (number2_current == NULL)?0:number2_current->number;

//计算加数1+加数2+进位

int result = number1 + number2 + carry;

//更新进位

carry = result/10;

//获取当前位除掉进位后的值

result = result % 10;

//如果尚未创建链表,说明当前是第一次进入循环,则创建头节点

if(result_head == NULL){

result_head = create_head(result);

result_tail = result_head;

}else{

//进入这里,说明链表已创建,可以直接创建新节点,并追加到原链表后面

create_node_to_tail(&result_tail,result);

}

//移动指针,进入下一次循环,加入非空判断,应对两个加数不一样长的情况

if(number1_current != NULL){

number1_current = number1_current->next;

}

if(number2_current != NULL){

number2_current = number2_current->next;

}

}

//结束循环后,如果进位大于0,则还需要再创建一个节点

if(carry > 0){

create_node_to_tail(&result_tail,carry);

}

//返回尾指针

return result_tail;

}

/**

* 输入大数

* return:输入后产生的链表的头指针

*

**/

Node * input_number(){

printf("%s","请输入加数\n");

//保存输入的数字的头指针和尾指针

Node * head = NULL;

Node * tail = NULL;

while(1){

//每次输入一个字符

char c;

scanf("%c",&c);

//0-9对应的asicc码值为48-57,在此范围内,说明输入的是数字

if(c >= 48 && c <= 57) {

//减去48,将char型转为数字

int number = c - 48;

//如果尚未创建链表,说明是第一次进入循环,则创建头节点

if(head == NULL){

head = create_head(number);

tail = head;

}else{

//进入到这里,说明链表已创建,可以直接创建新节点,并加到原链表的前面

//注:链表保存的数字,低位在前,高位在后,而输入数字时,高位先输入,低位后输入

//所以这里链表的结点要加到链表的最前面

create_node_to_head(&head,number);

}

}

//如果输入的是回车,则退出循环

else if(c == '\n'){

break;

}else{

//如果输入的不是上两者,则返回NULL

printf("%s","只可以输入数字\n");

return NULL;

}

}

return head;

}

/**

* 输出大数

* param:tail要输出的链表的尾指针,因为存放数据的时候,低位在前,高位在后,为了正常输出,需要从尾向头输出

*

**/

void output_number(Node * tail){

Node * current = tail;

//从尾到头,一个一个输出数字

while(current != NULL){

printf("%d",current->number);

current = current->prev;

}

}

void main(){

//依次输入加数,如果返回为NULL,则说明输入不合法,退出

Node * number1_head = input_number();

if(number1_head == NULL)

return;

Node * number2_head = input_number();

if(number2_head == NULL)

return;

//计算结果,并根据返回的尾指针输出数字

Node * result_tail = add_big(number1_head,number2_head);

output_number(result_tail);

}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值