C语言大数运算

唉唉,写了一些比较完备的c大数运算api

代码如下:

large_num.h

#ifndef LARGE_NUM_H
#define LARGE_NUM_H
#define LARGE_MAX 1024

typedef struct large_num_struct
{
    int p;
    int len;
    char large_num_arr[LARGE_MAX];
}large_num;

int is_zero(large_num*);
void is_len_overflow(int);
large_num str_to_large(char*);
large_num add_lar_lar(large_num*,large_num*);// +
large_num sub_lar_lar(large_num*,large_num*);// -
large_num mul_lar_int(large_num*,int);// *
large_num mul_lar_lar(large_num*,large_num*);// *
large_num div_lar_lar(large_num*,large_num*);// /
large_num mod_lar_lar(large_num*,large_num*);// %
large_num* compare_2lar(large_num*,large_num*);
void printf_lar(large_num*);
double large_to_sci_num(large_num*,int);

void add_lar_lar_p(large_num*,large_num*,large_num*);
void sub_lar_lar_p(large_num*,large_num*,large_num*);
void mul_lar_lar_p(large_num*,large_num*,large_num*);
void div_lar_lar_p(large_num*,large_num*,large_num*);

void add_self_lar_lar_p(large_num*,large_num*);
void sub_self_lar_lar_p(large_num*,large_num*);
void mul_self_lar_lar_p(large_num*,large_num*);

void add_self_lar_one_p(large_num*);

int strictly_larger(large_num*,large_num*);
int is_equal(large_num*,large_num*);

#endif

主代码部分,api

large_num_2.c

#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <string.h>
#include "large_num.h"
#define MAX(x,y) ((x)>(y)?(x):(y))

//"0" 的定义
//p=1,len=1,every number in arr is 0

int is_zero(large_num* num){
    int flag=0;
    if (num->len==1&&num->large_num_arr[0]==0)
    {
        flag=1;
    }

    return flag;  
}

void is_len_overflow(int len){
    if (len>LARGE_MAX)
    {
        printf("\nError:lar_len is overflow!\n");
        exit(1);
    }
    
}

large_num str_to_large(char* large_num_str){
    
    large_num l_n={.large_num_arr={0}};//初始化

    if (large_num_str[0]=='-')
    {
        l_n.len=strlen(large_num_str)-1;
        l_n.p=-1;

#ifdef STR_TO_LARGE
        printf("len=%d\n",l_n.len);
#endif

        for (int i = 0; i < l_n.len; i++)
        {
            l_n.large_num_arr[i]=large_num_str[l_n.len-i]-'0';

#ifdef STR_TO_LARGE1
        printf("flag:(arr,str)=(%d,%d)\n",l_n.large_num_arr[i],large_num_str[l_n.len-i]);
#endif

        }
        
    }
    else{
        l_n.len=strlen(large_num_str);
        l_n.p=1;
        for (int i = 0; i < l_n.len; i++)
        {
            l_n.large_num_arr[i]=large_num_str[l_n.len-1-i]-'0';
        }
        
    }

    is_len_overflow(l_n.len);
    return l_n;
}

void printf_lar(large_num* num){
    if (num->p==-1)//判断相等用==
    {
        printf("-");
    }

    for (size_t i = 0; i < num->len; i++)
    {
        char number_char=num->large_num_arr[num->len-1-i]+'0';
        putchar(number_char);
    }
    
}

large_num add_lar_lar(large_num* num1,large_num* num2){
    
    is_len_overflow(num1->len);
    is_len_overflow(num2->len);

    large_num result={.large_num_arr={0}};

    if ((num1->p)*(num2->p)>0)
    {
        result.p=num1->p;//一种+,一种-
        
        for (size_t i = 0; i < MAX(num1->len,num2->len); i++)
        {
            result.large_num_arr[i]+=num1->large_num_arr[i]+num2->large_num_arr[i];//要考虑result.large_num_arr[i]=1的情况
            if (result.large_num_arr[i]>=10)
            {
                result.large_num_arr[i+1]+=1;
                result.large_num_arr[i]%=10;
            }
            
        }
        
        if (result.large_num_arr[MAX(num1->len,num2->len)]!=0)//注意len与位次的换算
        {
            result.len=MAX(num1->len,num2->len)+1;
        }
        else result.len=MAX(num1->len,num2->len);
        
    }
    else{
        if (num1->p>0)
        {
            num2->p=1;
            result=sub_lar_lar(num1,num2);
            num2->p=-1;
        }
        else if (num1->p<0)
        {
            num1->p=1;
            result=sub_lar_lar(num2,num1);
            num1->p=-1;
        }
        
        
    }

    is_len_overflow(result.len);
    return result;

}

large_num* compare_2lar(large_num*num1,large_num* num2){//相等时,返回num1

    is_len_overflow(num1->len);
    is_len_overflow(num2->len);

    large_num* result=NULL;
    if (num1->len>num2->len)
    {
        result=num1;
    }
    else if (num1->len<num2->len)
    {
        result=num2;
    }
    else{
        for (size_t i = 0; i < num1->len; i++)
        {
            if ((num1->large_num_arr[num1->len-1-i])>(num2->large_num_arr[num2->len-1-i]))
            {
                result=num1;
                break;
            }
            else if ((num1->large_num_arr[num1->len-1-i])<(num2->large_num_arr[num2->len-1-i]))
            {
                result=num2;
                break;
            }
            
            if ((i==num1->len-1)&&((num1->large_num_arr[num1->len-1-i])==(num2->large_num_arr[num2->len-1-i])))
            {
                result=num1;
            }
            
        }
        
    }
    
    return result;
}

large_num sub_lar_lar(large_num* num1,large_num* num2){

    is_len_overflow(num1->len);
    is_len_overflow(num2->len);

    large_num result={.large_num_arr={0}};
    large_num* larger=compare_2lar(num1,num2);
    large_num* smaller=NULL;

    if (larger==num1)//比较大小
    {
        smaller=num2;
    }
    else smaller=num1;
    
    if ((num1->p)*(num2->p)>0)
    {

        if (num1->p>0)//确定符号
        {
            if (num1==larger)
            {
                result.p=1;
            }
            else if (num2==larger)
            {
                result.p=-1;
            }
        }
        else if (num1->p<0)
        {
            if (num1==smaller)
            {
                result.p=1;
            }
            else result.p=-1;
        }
        
        for (size_t i = 0; i < larger->len; i++)//确定数组
        {
            result.large_num_arr[i]+=larger->large_num_arr[i]-smaller->large_num_arr[i];
            if (result.large_num_arr[i]<0)
            {
                result.large_num_arr[i]+=10;
                result.large_num_arr[i+1]-=1;
            }
        }
        
        for (size_t i = 0; i < larger->len; i++)//确定长度
        {
            if (result.large_num_arr[larger->len-1-i]!=0)
            {
                result.len=larger->len-i;
                break;
            }

            if ((i==larger->len-1)&&(result.large_num_arr[0]==0))
            {
                result.len=1;
            }
            
            
        }
        
        if (result.len==1&&result.large_num_arr[0]==0)//0的符号设为1
        {
            result.p=1;
        }
        
    }
    else{
        result.p=num1->p;

        if (num1->p<0)
        {
            num2->p=-1;
            result=add_lar_lar(num1,num2);
            num2->p=1;
        }
        else if (num1->p>0)
        {
            num2->p=1;
            result=add_lar_lar(num1,num2);
            num2->p=-1;
        }
        
    }
    
    is_len_overflow(result.len);
    return result;
}

large_num mul_lar_int(large_num* num,int n){

    is_len_overflow(num->len);

    large_num result={.large_num_arr={0}};
    large_num temp;
    int n_abs=abs(n);

    if (n==0)
    {
        result.len=1;
    }
    else if (n_abs==1)
    {
        result=*num;
    }
    else{
        result=*num;
        for (size_t i = 0; i < n_abs-1; i++)
        {
            temp=add_lar_lar(&result,num);
            result=temp;
        }
        
    }
    

    if ((num->p)*n>=0)//符号
    {
        result.p=1;
    }
    else result.p=-1;
    
    is_len_overflow(result.len);
    return result;
    
}

large_num mul_lar_lar(large_num* num1,large_num* num2){

    is_len_overflow(num1->len);
    is_len_overflow(num2->len);

    large_num result={.large_num_arr={0}};

    result.p=(num1->p)*(num2->p);
    
    for (size_t i = 0; i < num1->len; i++)
    {
        for (size_t j = 0; j < num2->len; j++)
        {
            result.large_num_arr[i+j]+=((num1->large_num_arr[i])*(num2->large_num_arr[j]));
            result.large_num_arr[i+j+1]+=result.large_num_arr[i+j]/10;
            result.large_num_arr[i+j]%=10;
        }
    }
    
    if (result.large_num_arr[num1->len+num2->len-1]==0)
    {
        result.len=num1->len+num2->len-1;
    }
    else{
        result.len=num1->len+num2->len;
    }
    
    is_len_overflow(result.len);
    return result;
    
}

large_num div_lar_lar(large_num* num1,large_num* num2){

    is_len_overflow(num1->len);
    is_len_overflow(num2->len);

    large_num result={.large_num_arr={0}};
    large_num* larger=compare_2lar(num1,num2);

    result.p=(num1->p)*(num2->p);

    int num1_p=num1->p;
    int num2_p=num2->p;
    num1->p=1,num2->p=1;
    large_num temp_1=*num1;
    large_num temp_2=*num2;
    
    //计算数组及长度
    if (num2==larger)//结果为0
    {
        result.len=1;
        result.p=1;
    }
    else{
        if (num1->len==num2->len)
        {
            result.len=1;
            while (temp_1.p>0)
            {
                temp_1=sub_lar_lar(&temp_1,num2);
                result.large_num_arr[0]++;
            }
            result.large_num_arr[0]--;
        }
        else{

            for (size_t i = 0; i < num1->len-num2->len+1; i++)
            {
                
                if (i!=num1->len-num2->len)
                {
                    for (size_t j = 0; j < num2->len; j++)//将num2数位左移(当时没考虑不进位的情况)
                    {
                        temp_2.large_num_arr[num1->len-1-i-j]=num2->large_num_arr[num2->len-1-j];
                        temp_2.large_num_arr[num2->len-1-j]=0;
                    }   
                }

                temp_2.len=num1->len-i;

                while (temp_1.p>0)
                {
                    temp_1=sub_lar_lar(&temp_1,&temp_2);
                    result.large_num_arr[num1->len-num2->len-i]++;
                }

                result.large_num_arr[num1->len-num2->len-i]--;//补偿多减的一个
                temp_1=add_lar_lar(&temp_1,&temp_2);

                temp_2=*num2;//重置num2
                
            }
            
            if (result.large_num_arr[num1->len-num2->len]!=0)//长度
            {
                result.len=num1->len-num2->len+1;
            }
            else result.len=num1->len-num2->len;

            
        }
        
    }
    
    num1->p=num1_p,num2->p=num2_p;
    is_len_overflow(result.len);
    return result;

}

large_num mod_lar_lar(large_num* num1,large_num* num2){

    is_len_overflow(num1->len);
    is_len_overflow(num2->len);

    large_num quotient=div_lar_lar(num1,num2);
    large_num product=mul_lar_lar(&quotient,num2);
    large_num result=sub_lar_lar(num1,&product);
    int num2_p=num2->p;

    num2->p=1;

    if (result.p<0)
    {
        result=add_lar_lar(&result,num2);
    }
    
    num2->p=num2_p;

    is_len_overflow(result.len);
    return result;

}

double large_to_sci_num(large_num* num,int eps){//未完
    double result;
    int index=num->len-1;
    double front=0;

    if ((num->len)==1)
    {
        front=(double) num->large_num_arr[0];
        result=front;
    }
    else{
        for (size_t i = 0; i < eps; i++)
        {
            front+=pow(10,i)*num->large_num_arr[i];
        }

        result=front*pow(10,index);
        
    }

    return result;
    
}

void add_lar_lar_p(large_num* num1,large_num* num2,large_num* result){

    is_len_overflow(num1->len);
    is_len_overflow(num2->len);

    for (size_t i = 0; i < LARGE_MAX; i++)
    {
        result->large_num_arr[i]=0;
    }
    

    if ((num1->p)*(num2->p)>0)
    {
        result->p=num1->p;//一种+,一种-
        
        for (size_t i = 0; i < MAX(num1->len,num2->len); i++)
        {
            result->large_num_arr[i]+=num1->large_num_arr[i]+num2->large_num_arr[i];//要考虑result.large_num_arr[i]=1的情况
            if (result->large_num_arr[i]>=10)
            {
                result->large_num_arr[i+1]+=1;
                result->large_num_arr[i]%=10;
            }
            
        }
        
        if (result->large_num_arr[MAX(num1->len,num2->len)]!=0)//注意len与位次的换算
        {
            result->len=MAX(num1->len,num2->len)+1;
        }
        else result->len=MAX(num1->len,num2->len);
        
    }
    else{
        if (num1->p>0)
        {
            num2->p=1;
            sub_lar_lar_p(num1,num2,result);
            num2->p=-1;
        }
        else if (num1->p<0)
        {
            num1->p=1;
            sub_lar_lar_p(num2,num1,result);
            num1->p=-1;
        }   
    }
    is_len_overflow(result->len);
}

void sub_lar_lar_p(large_num* num1,large_num* num2,large_num* result){

    is_len_overflow(num1->len);
    is_len_overflow(num2->len);

    for (size_t i = 0; i < LARGE_MAX; i++)
    {
        result->large_num_arr[i]=0;
    }

    large_num* larger=compare_2lar(num1,num2);
    large_num* smaller=NULL;

    if (larger==num1)//比较大小
    {
        smaller=num2;
    }
    else smaller=num1;
    
    if ((num1->p)*(num2->p)>0)
    {

        if (num1->p>0)//确定符号
        {
            if (num1==larger)
            {
                result->p=1;
            }
            else if (num2==larger)
            {
                result->p=-1;
            }
        }
        else if (num1->p<0)
        {
            if (num1==smaller)
            {
                result->p=1;
            }
            else result->p=-1;
        }
        
        for (size_t i = 0; i < larger->len; i++)//确定数组
        {
            result->large_num_arr[i]+=larger->large_num_arr[i]-smaller->large_num_arr[i];
            if (result->large_num_arr[i]<0)
            {
                result->large_num_arr[i]+=10;
                result->large_num_arr[i+1]-=1;
            }
        }
        
        for (size_t i = 0; i < larger->len; i++)//确定长度
        {
            if (result->large_num_arr[larger->len-1-i]!=0)
            {
                result->len=larger->len-i;
                break;
            }

            if ((i==larger->len-1)&&(result->large_num_arr[0]==0))
            {
                result->len=1;
            }
            
            
        }
        
        if (result->len==1&&result->large_num_arr[0]==0)//0的符号设为1
        {
            result->p=1;
        }
        
    }
    else{
        result->p=num1->p;

        if (num1->p<0)
        {
            num2->p=-1;
            add_lar_lar_p(num1,num2,result);
            num2->p=1;
        }
        else if (num1->p>0)
        {
            num2->p=1;
            add_lar_lar_p(num1,num2,result);
            num2->p=-1;
        }
        
    }
    is_len_overflow(result->len);
}

void mul_lar_lar_p(large_num* num1,large_num* num2,large_num* result){

    is_len_overflow(num1->len);
    is_len_overflow(num2->len);

    for (size_t i = 0; i < LARGE_MAX; i++)
    {
        result->large_num_arr[i]=0;
    }

    result->p=(num1->p)*(num2->p);
    
    for (size_t i = 0; i < num1->len; i++)
    {
        for (size_t j = 0; j < num2->len; j++)
        {
            result->large_num_arr[i+j]+=((num1->large_num_arr[i])*(num2->large_num_arr[j]));
            result->large_num_arr[i+j+1]+=result->large_num_arr[i+j]/10;
            result->large_num_arr[i+j]%=10;
        }
    }
    
    if (result->large_num_arr[num1->len+num2->len-1]==0)
    {
        result->len=num1->len+num2->len-1;
    }
    else{
        result->len=num1->len+num2->len;
    }
    is_len_overflow(result->len);
}

void div_lar_lar_p(large_num* num1,large_num* num2,large_num* result){

    is_len_overflow(num1->len);
    is_len_overflow(num2->len);

    for (size_t i = 0; i < LARGE_MAX; i++)
    {
        result->large_num_arr[i]=0;
    }

    large_num* larger=compare_2lar(num1,num2);

    result->p=(num1->p)*(num2->p);

    int num1_p=num1->p;
    int num2_p=num2->p;
    num1->p=1,num2->p=1;
    large_num temp_1=*num1;
    large_num temp_2=*num2;
    
    //计算数组及长度
    if (num2==larger)//结果为0
    {
        result->len=1;
        result->p=1;
    }
    else{
        if (num1->len==num2->len)
        {
            result->len=1;
            while (temp_1.p>0)
            {
                temp_1=sub_lar_lar(&temp_1,num2);
                result->large_num_arr[0]++;
            }
            result->large_num_arr[0]--;
        }
        else{

            for (size_t i = 0; i < num1->len-num2->len+1; i++)
            {
                
                if (i!=num1->len-num2->len)
                {
                    for (size_t j = 0; j < num2->len; j++)//将num2数位左移(当时没考虑不进位的情况)
                    {
                        temp_2.large_num_arr[num1->len-1-i-j]=num2->large_num_arr[num2->len-1-j];
                        temp_2.large_num_arr[num2->len-1-j]=0;
                    }   
                }

                temp_2.len=num1->len-i;

                while (temp_1.p>0)
                {
                    temp_1=sub_lar_lar(&temp_1,&temp_2);
                    result->large_num_arr[num1->len-num2->len-i]++;
                }

                result->large_num_arr[num1->len-num2->len-i]--;//补偿多减的一个
                temp_1=add_lar_lar(&temp_1,&temp_2);

                temp_2=*num2;//重置num2
                
            }
            
            if (result->large_num_arr[num1->len-num2->len]!=0)//长度
            {
                result->len=num1->len-num2->len+1;
            }
            else result->len=num1->len-num2->len;

            
        }
        
    }
    
    num1->p=num1_p,num2->p=num2_p;
    is_len_overflow(result->len);
    
}

void add_self_lar_lar_p(large_num* num1_result,large_num* num2){
    large_num num1=*num1_result;
    add_lar_lar_p(&num1,num2,num1_result);
}

void sub_self_lar_lar_p(large_num* num1_result,large_num* num2){
    large_num num1=*num1_result;
    sub_lar_lar_p(&num1,num2,num1_result);
}

void mul_self_lar_lar_p(large_num* num1_result,large_num* num2){
    large_num num1=*num1_result;
    mul_lar_lar_p(&num1,num2,num1_result);
}

void add_self_lar_one_p(large_num* num){
    is_len_overflow(num->len);
    num->large_num_arr[0]++;
    for (size_t i = 0; i < num->len; i++)
    {
        if (num->large_num_arr[i]>=10)
        {
            num->large_num_arr[i]%=10;
            num->large_num_arr[i+1]+=1;
        }
        
    }
    
}

int strictly_larger(large_num* num1,large_num* num2){
    int result;
    is_len_overflow(num1->len);
    is_len_overflow(num2->len);

    large_num* larger=compare_2lar(num1,num2);
    large_num* other=compare_2lar(num2,num1);
    if (larger==other&&larger==num1)
    {
        result=1;
    }
    else{
        result=0;
    }
    
    return result;
}

int is_equal(large_num* num1,large_num* num2){
    int result;
    is_len_overflow(num1->len);
    is_len_overflow(num2->len);

    large_num* larger=compare_2lar(num1,num2);
    large_num* other=compare_2lar(num2,num1);
    if (larger==num1&&other==num2)
    {
        result=1;
    }
    else{
        result=0;
    }

    return result;
}

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值