【问题标题】:How do you properly implement turning an int into a string?您如何正确实现将 int 转换为字符串?
【发布时间】:2015-07-10 01:30:25
【问题描述】:

我正在编写一个操作系统,我需要能够打印添加的变量。我有一个可用的 atoi 函数,所以我将它反转给我一个 itoa 函数。没有办法访问空闲内存,所以我需要弄清楚位数才能创建适当大小的 char 数组。我想我需要除以 10 才能得到它,然后将值模数到正确的位置。到目前为止,这是我的 c 代码:

char* itoa(int res) {
    int size = 0;
    int t = res;

    while(t / 10 != 0) {
        t = t/10;
        size ++;
    }
    char ret[size+1];
    ret[size] = '\0';

    t = res;
    int i = size - 1;
    while(i > 0) {
        ret[i] = t % 10;
        t = t/10;
        i--;
    }

    return ret;
}

截至目前,它什么也没打印。它有什么问题?

【问题讨论】:

  • 好吧,一方面,您返回的是临时值。
  • 否定 int 失败。
  • 什么意思? - @imallett
  • char ret[] 在函数完成后不再可用。返回指向它的指针不起作用。
  • 在开始编写操作系统之前,您不应该了解基本的 C 概念吗?

标签: c osdev itoa


【解决方案1】:

它有一些错误。这里至少有一个正数的工作版本:

char* itoa(int res) {
    int size = 0;
    int t = res;

    while(t / 10 != 0) {
        t = t/10;
        size++;
    }
    static char ret[64];
    size++;
    ret[size] = '\0';
    t = res;
    int i = size - 1;
    while(i >= 0) {
        ret[i] = (t % 10) + '0';
        t = t/10;
        i--;
    }

    return ret;
}

【讨论】:

    【解决方案2】:

    这里有很多问题。最明显的是:

    • 您正在返回一个临时值。 ret 在栈上,弹出后不存在。
    • 您正在尝试在堆栈上动态分配某些内容。这实际上可能有效,但除非您知道自己在做什么,否则您不应该这样做。

    放在一起,这些基本上会扼杀您的实施。因此,为了提供帮助,这里有一些 un经过测试的代码:

    void putc(char c) {
        /*Output "c" via BIOS interrupt or VGA write.  Or whatever.*/
    }
    void print(int num) {
        if (num!=0) {
            /*Largest num is `2,147,483,64(7|8)`*/
            char temp[10];
            int i = 0;
            if (num<0) { putc('-'); num=-num; }
            if (num>0); else { temp[i++]='8'; num=-(num/10); } //signed wraparound
            while (num>0) {
                temp[i++] = num%10 + '0';
                num /= 10;
            }
            while (--i>=0) putc(temp[i]);
        } else putc('0');
    }
    

    【讨论】:

    • 注意:INT_MIN 失败。候选修复:if (num&lt;0) putc('-'); else num=-num; char temp[10]; int i = 0; do { temp[i++] = '0' - num%10; num /= 10; } while (num);
    • @chux 为未来人们的利益而修复。现在也更加分支预测器友好。我喜欢- 订单在这里的重要性。 :D
    • 这真的很有帮助,谢谢。我做错了,因为我不需要将所有“字符串”转换为整数;我只需要输出整数(现在无论如何)。所以谢谢。
    【解决方案3】:

    如果您可以忍受调用方为所有预期输出提供足够大的缓冲区,那么您可以:

    #include <stdio.h> 
    
        char * rIntToAscii(int num, char * result){ 
            if( num == 0 ) return result; 
            else{ 
                 result=rIntToAscii( num/10, result );
                 *result = '0'+num%10;
                return result+1; 
            } 
        };
    
        void intToAscii(int num,char *output){
          if (num==0){
            *output++='0';
            *output='\0';
          }
            else
            {
              if(num<0){
                *output++='-';
                num=-num;
              };
              *rIntToAscii(num, output) = '\0';
            };
        };
    
        int main(void) 
        { 
            int test = -10;
            char testOutput[ 32 ];
            intToAscii(test,testOutput);
            printf( "%s", testOutput );
            return 0; 
        }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2015-11-12
      • 2018-05-08
      • 1970-01-01
      • 1970-01-01
      • 2022-06-27
      • 1970-01-01
      相关资源
      最近更新 更多