Как преобразовать unsigned long в строку

На языке C, как мне преобразовать значение unsigned long в строку (char *) и сохранить мой исходный код переносимым или просто перекомпилировать его для работы на другой платформе (без перезаписи кода?

Например, если у меня есть sprintf(buffer, format, value), как определить размер буфера с независимым от платформы образом?

Ответы

Ответ 1

const int n = snprintf(NULL, 0, "%lu", ulong_value);
assert(n > 0);
char buf[n+1];
int c = snprintf(buf, n+1, "%lu", ulong_value);
assert(buf[n] == '\0');
assert(c == n);

Ответ 2

Стандартным подходом является использование sprintf(buffer, "%lu", value); для записи строкового представления value в buffer. Однако переполнение является потенциальной проблемой, так как sprintf будет радостно (и неосознанно) писать в конце вашего буфера.

На самом деле это большая слабость sprintf, частично фиксированная на С++ с использованием потоков, а не буферов. Обычный "ответ" заключается в том, чтобы выделить очень щедрый буфер, который вряд ли переполнится, пусть это приведет к выводу sprintf, а затем использовать strlen для определения фактической длины строки, вызванной буфером (size size + 1) и скопировать строку в эту,

Этот сайт обсуждает эту и связанные с этим проблемы в некоторой степени.

Некоторые библиотеки предлагают snprintf как альтернативу, которая позволяет указать максимальный размер буфера.

Ответ 3

вы можете написать функцию, которая преобразует из unsigned long в str, аналогичную библиотечной функции ltostr.

char *ultostr(unsigned long value, char *ptr, int base)
{
  unsigned long t = 0, res = 0;
  unsigned long tmp = value;
  int count = 0;

  if (NULL == ptr)
  {
    return NULL;
  }

  if (tmp == 0)
  {
    count++;
  }

  while(tmp > 0)
  {
    tmp = tmp/base;
    count++;
  }

  ptr += count;

  *ptr = '\0';

  do
  {
    res = value - base * (t = value / base);
    if (res < 10)
    {
      * -- ptr = '0' + res;
    }
    else if ((res >= 10) && (res < 16))
    {
        * --ptr = 'A' - 10 + res;
    }
  } while ((value = t) != 0);

  return(ptr);
}

вы можете сослаться на мой блог здесь, который объясняет реализацию и использование с примером.

Ответ 4

char buffer [50];

unsigned long a = 5;

int n=sprintf (buffer, "%lu", a);

Ответ 5

Попробуйте использовать sprintf:

unsigned long x=1000000;
char buffer[21];
sprintf(buffer,"%lu", x);

Edit:

Обратите внимание, что вам необходимо заранее выделить буфер, и не знаешь, как долго будут на самом деле числа, когда вы это сделаете. Я предполагаю 32bit long s, который может производить цифры размером до 10 цифр.

См. Carl Smotricz для лучшего объяснения затронутых проблем.

Ответ 6

Для длинного значения вам нужно добавить информацию длины 'l' и 'u' для целых чисел без знака,

в качестве ссылки доступных опций см. sprintf

#include <stdio.h>

    int main ()
    {
      unsigned long lval = 123;
      char buffer [50];
      sprintf (buffer, "%lu" , lval );
     }