C 将输入读入动态大小的整数?

C 将输入读入动态大小的整数?,c,pointers,int,stdin,C,Pointers,Int,Stdin,我需要从stdin中读取大量数据,以下是我迄今为止的代码: int main() { int x; int* n1; scanf("%d", &x); // I get the number of digits the integer will have n1 = malloc(x * sizeof(int)); // I resize the integer pointer } 所以我的问题是如何从stdin中读取这个可能很大的int?intx; i

我需要从stdin中读取大量数据,以下是我迄今为止的代码:

int main() {
    int x;
    int* n1;
    scanf("%d", &x); // I get the number of digits the integer will have

    n1 = malloc(x * sizeof(int)); // I resize the integer pointer
}
所以我的问题是如何从stdin中读取这个可能很大的int?

intx;
int x;
int* n1;
int i;
scanf("%d", &x);

n1 = malloc(x * sizeof(int));

for(i = 0; i < x; ++i){
    scanf("%1d", &n1[i]);//Read (unsigned) one digit
}
for(i = 0; i < x; ++i){
    printf("%d", n1[i]);
}
puts("");
int*n1; int i; scanf(“%d”和&x); n1=malloc(x*sizeof(int)); 对于(i=0;i
intx;
int*n1;
int i;
scanf(“%d”和&x);
n1=malloc(x*sizeof(int));
对于(i=0;i
按照您现在的设计方式,您将有一个指向
int
的指针,换句话说:一个int数组。可以存储数字的最大整数类型是
long
(其大小取决于机器,在64位机器上通常为8字节)


您也可以考虑将数字存储在一个字符串中(在分配了<代码> char */COD>)之后,或者,如您所说,在一个数组的<代码> int S中,其中每个数组元素都包含任意数量的数字(然后我建议使用<代码> GETCHARE)(<代码> >和<代码> ATOI()> <代码>函数,而不是<代码> SCAFF()>代码>.

按照您现在的设计方式,您将有一个指向
int
的指针,换句话说:一个int数组。可以存储数字的最大整数类型是
long
(其大小取决于机器,在64位机器上通常为8字节)


您也可以考虑将数字存储在一个字符串中(在分配了<代码> char */COD>)之后,或者,如您所说,在一个数组的<代码> int S中,其中每个数组元素都包含任意数量的数字(然后我建议使用<代码> GETCHARE)(<代码> >和<代码> ATOI()> <代码>函数,而不是<代码> SCAFF()>代码>.

在C中没有“动态大小的int”这样的东西。正如其他人所建议的,根据您的使用情况,将数字作为字符串读取可能是您想要的。(如果为此使用
scanf
,请注意缓冲区溢出。)


如果您需要对数字进行算术运算,您可能希望使用现有的库(例如此库),以从现有的问题解决方案中获益。您也可以自己重新实现libgmp的功能,但除非您将此作为一个学习练习,否则没有理由这样做。

在C中没有“动态大小的int”这样的东西。正如其他人所建议的,根据您的使用情况,将数字作为字符串读取可能是您想要的。(如果为此使用
scanf
,请注意缓冲区溢出。)


如果您需要对数字进行算术运算,您可能希望使用现有的库(例如此库),以从现有的问题解决方案中获益。您也可以自己重新实现libgmp的功能,但除非您将此作为学习练习,否则没有理由这样做。

处理非常大的数字的最可靠的方法是使用“bignum.c”,可在以下网站获得:

引用的代码是一个完整的程序,。但是函数和结构可以自由使用

你会在那里找到什么:

/*  bignum.c
    Implementation of large integer arithmetic: addition, subtraction,
        multiplication, and division.

    begun: February 7, 2002
    by: Steven Skiena
*/

/*
Copyright 2003 by Steven S. Skiena; all rights reserved. 

Permission is granted for use in non-commerical applications
provided this copyright notice remains intact and unchanged.

This program appears in my book:

"Programming Challenges: The Programming Contest Training Manual"
by Steven Skiena and Miguel Revilla, Springer-Verlag, New York 2003.

See our website www.programming-challenges.com for additional information.

This book can be ordered from Amazon.com at

http://www.amazon.com/exec/obidos/ASIN/0387001638/thealgorithmrepo/

*/


#include <stdio.h>

#define MAXDIGITS   100     /* maximum length bignum */ 

#define PLUS        1       /* positive sign bit */
#define MINUS       -1      /* negative sign bit */

typedef struct {
        char digits[MAXDIGITS];         /* represent the number */
    int signbit;            /* 1 if positive, -1 if negative */ 
        int lastdigit;          /* index of high-order digit */
} bignum;


print_bignum(bignum *n)
{
    int i;

    if (n->signbit == MINUS) printf("- ");
    for (i=n->lastdigit; i>=0; i--)
        printf("%c",'0'+ n->digits[i]);

    printf("\n");
}

int_to_bignum(int s, bignum *n)
{
    int i;              /* counter */
    int t;              /* int to work with */

    if (s >= 0) n->signbit = PLUS;
    else n->signbit = MINUS;

    for (i=0; i<MAXDIGITS; i++) n->digits[i] = (char) 0;

    n->lastdigit = -1;

    t = abs(s);

    while (t > 0) {
        n->lastdigit ++;
        n->digits[ n->lastdigit ] = (t % 10);
        t = t / 10;
    }

    if (s == 0) n->lastdigit = 0;
}

initialize_bignum(bignum *n)
{
    int_to_bignum(0,n);
}


int max(int a, int b)
{
    if (a > b) return(a); else return(b);
}

/*  c = a +-/* b;   */

add_bignum(bignum *a, bignum *b, bignum *c)
{
    int carry;          /* carry digit */
    int i;              /* counter */

    initialize_bignum(c);

    if (a->signbit == b->signbit) c->signbit = a->signbit;
    else {
        if (a->signbit == MINUS) {
            a->signbit = PLUS;
            subtract_bignum(b,a,c);
            a->signbit = MINUS;
        } else {
                        b->signbit = PLUS;
                        subtract_bignum(a,b,c);
                        b->signbit = MINUS;
        }
        return;
    }

    c->lastdigit = max(a->lastdigit,b->lastdigit)+1;
    carry = 0;

    for (i=0; i<=(c->lastdigit); i++) {
        c->digits[i] = (char) (carry+a->digits[i]+b->digits[i]) % 10;
        carry = (carry + a->digits[i] + b->digits[i]) / 10;
    }

    zero_justify(c);
}


subtract_bignum(bignum *a, bignum *b, bignum *c)
{
    int borrow;         /* has anything been borrowed? */
    int v;              /* placeholder digit */
    int i;              /* counter */

    initialize_bignum(c);

    if ((a->signbit == MINUS) || (b->signbit == MINUS)) {
                b->signbit = -1 * b->signbit;
                add_bignum(a,b,c);
                b->signbit = -1 * b->signbit;
        return;
        }

    if (compare_bignum(a,b) == PLUS) {
        subtract_bignum(b,a,c);
        c->signbit = MINUS;
        return;
    }

        c->lastdigit = max(a->lastdigit,b->lastdigit);
        borrow = 0;

        for (i=0; i<=(c->lastdigit); i++) {
        v = (a->digits[i] - borrow - b->digits[i]);
        if (a->digits[i] > 0)
            borrow = 0;
        if (v < 0) {
            v = v + 10;
            borrow = 1;
        }

                c->digits[i] = (char) v % 10;
        }

    zero_justify(c);
}

compare_bignum(bignum *a, bignum *b)
{
    int i;              /* counter */

    if ((a->signbit == MINUS) && (b->signbit == PLUS)) return(PLUS);
    if ((a->signbit == PLUS) && (b->signbit == MINUS)) return(MINUS);

    if (b->lastdigit > a->lastdigit) return (PLUS * a->signbit);
    if (a->lastdigit > b->lastdigit) return (MINUS * a->signbit);

    for (i = a->lastdigit; i>=0; i--) {
        if (a->digits[i] > b->digits[i]) return(MINUS * a->signbit);
        if (b->digits[i] > a->digits[i]) return(PLUS * a->signbit);
    }

    return(0);
}

zero_justify(bignum *n)
{
    while ((n->lastdigit > 0) && (n->digits[ n->lastdigit ] == 0))
        n->lastdigit --;

        if ((n->lastdigit == 0) && (n->digits[0] == 0))
        n->signbit = PLUS;  /* hack to avoid -0 */
}


digit_shift(bignum *n, int d)       /* multiply n by 10^d */
{
    int i;              /* counter */

    if ((n->lastdigit == 0) && (n->digits[0] == 0)) return;

    for (i=n->lastdigit; i>=0; i--)
        n->digits[i+d] = n->digits[i];

    for (i=0; i<d; i++) n->digits[i] = 0;

    n->lastdigit = n->lastdigit + d;
}



multiply_bignum(bignum *a, bignum *b, bignum *c)
{
    bignum row;         /* represent shifted row */
    bignum tmp;         /* placeholder bignum */
    int i,j;            /* counters */

    initialize_bignum(c);

    row = *a;

    for (i=0; i<=b->lastdigit; i++) {
        for (j=1; j<=b->digits[i]; j++) {
            add_bignum(c,&row,&tmp);
            *c = tmp;
        }
        digit_shift(&row,1);
    }

    c->signbit = a->signbit * b->signbit;

    zero_justify(c);
}


divide_bignum(bignum *a, bignum *b, bignum *c)
{
        bignum row;                     /* represent shifted row */
        bignum tmp;                     /* placeholder bignum */
    int asign, bsign;       /* temporary signs */
        int i,j;                        /* counters */

    initialize_bignum(c);

    c->signbit = a->signbit * b->signbit;

    asign = a->signbit;
    bsign = b->signbit;

    a->signbit = PLUS;
        b->signbit = PLUS;

    initialize_bignum(&row);
    initialize_bignum(&tmp);

    c->lastdigit = a->lastdigit;

    for (i=a->lastdigit; i>=0; i--) {
        digit_shift(&row,1);
        row.digits[0] = a->digits[i];
        c->digits[i] = 0;
        while (compare_bignum(&row,b) != PLUS) {
            c->digits[i] ++;
            subtract_bignum(&row,b,&tmp);
            row = tmp;
        }
    }

    zero_justify(c);

    a->signbit = asign;
    b->signbit = bsign;
}



main()
{
    int a,b;
    bignum n1,n2,n3,zero;

    while (scanf("%d %d\n",&a,&b) != EOF) {
        printf("a = %d    b = %d\n",a,b);
        int_to_bignum(a,&n1);
        int_to_bignum(b,&n2);

        add_bignum(&n1,&n2,&n3);
        printf("addition -- ");
        print_bignum(&n3);

        printf("compare_bignum a ? b = %d\n",compare_bignum(&n1, &n2));

        subtract_bignum(&n1,&n2,&n3);
        printf("subtraction -- ");
        print_bignum(&n3);

                multiply_bignum(&n1,&n2,&n3);
        printf("multiplication -- ");
                print_bignum(&n3);

        int_to_bignum(0,&zero);
        if (compare_bignum(&zero, &n2) == 0)
            printf("division -- NaN \n");
                else {
            divide_bignum(&n1,&n2,&n3);
            printf("division -- ");
                    print_bignum(&n3);
        }
        printf("--------------------------\n");
    }
}
/*bignum.c
大整数算法的实现:加法、减法、,
乘法和除法。
开始日期:2002年2月7日
作者:史蒂文·斯基纳
*/
/*
史蒂文S.斯基纳2003年版权所有;版权所有。
允许在非商业应用中使用
前提是本版权声明保持不变。
此程序出现在我的书中:
“编程挑战:编程竞赛培训手册”
史蒂文·斯基纳和米格尔·雷维拉合著,斯普林格·维拉格,纽约,2003年。
有关更多信息,请访问我们的网站www.programming-challenges.com。
本书可从Amazon.com订购,网址为
http://www.amazon.com/exec/obidos/ASIN/0387001638/thealgorithmrepo/
*/
#包括
#定义MAXDIGITS 100/*最大长度bignum*/
#定义+1/*正号位*/
#定义负-1/*负号位*/
类型定义结构{
字符数字[MAXDIGITS];/*表示数字*/
int signbit;/*1如果为正,-1如果为负*/
int lastdigit;/*高阶数字的索引*/
}bignum;
打印bignum(bignum*n)
{
int i;
如果(n->signbit==负)printf(“-”);
对于(i=n->lastdigit;i>=0;i--)
printf(“%c”,“0”+n->数字[i]);
printf(“\n”);
}
int_to_bignum(int s,bignum*n)
{
int i;/*计数器*/
int t;/*要使用的int*/
如果(s>=0)n->signbit=PLUS;
否则n->signbit=负;
对于(i=0;idigits[i]=(char)0;
n->lastdigit=-1;
t=绝对值(s);
而(t>0){
n->lastdigit++;
n->digits[n->lastDigits]=(t%10);
t=t/10;
}
如果(s==0)n->lastdigit=0;
}
初始化_bignum(bignum*n)
{
int-to-bignum(0,n);
}
最大整数(整数a,整数b)
{
如果(a>b)返回(a);否则返回(b);
}
/*c=a+-/*b*/
添加_bignum(bignum*a、bignum*b、bignum*c)
{
整数进位;/*进位数字*/
int i;/*计数器*/
初始化_bignum(c);
如果(a->signbit==b->signbit)c->signbit=a->signbit;
否则{
如果(a->符号位==负){
a->signbit=PLUS;
减去_bignum(b,a,c);
a->signbit=负;
}否则{
b->signbit=PLUS;
减去_bignum(a,b,c);
b->符号位=负;
}
返回;
}
c->lastdigit=max(a->lastdigit,b->lastdigit)+1;
进位=0;
对于(i=0;ilastdigit);i++){
c->数字[i]=(字符)(进位+a->数字[i]+b->数字[i])%10;
进位=(进位+a->数字[i]+b->数字[i])/10;
}
零(c);
}
减去bignum(bignum*a,bignum*b,bignum*c)
{
int BROW;/*是否有任何错误