Самый простой способ конвертировать int в строку в C ++

1575

Какой самый простой способ конвертировать intв эквивалент stringв C ++. Я знаю о двух методах. Есть ли более простой способ?

(1)

int a = 10;
char *intStr = itoa(a);
string str = string(intStr);

(2)

int a = 10;
stringstream ss;
ss << a;
string str = ss.str();
Nemo
источник
4
Я думаю, что оба метода вы дали хорошие решения. это зависит от контекста, где вам нужно это сделать. Если вы уже работаете с потоками, например, читаете или пишете файл, тогда ваш второй метод - лучший. Если вам нужно передать int как строку в аргумент функции, то itoa может быть простым способом. Но в большинстве случаев при работе с файлами происходит преобразование int в строку, поэтому потоки являются подходящими.
Шарль Брюне
41
Как вариант 1 вообще работает для вас? Это мое понимание, которое itoa()принимает три параметра.
b1nary.atr0phy
1
Итоа будет быстрее, чем эквивалент потока. Существуют также способы повторного использования строкового буфера с методом itoa (избегая выделения кучи, если вы часто генерируете строки. Например, для некоторых быстро обновляемых числовых выходных данных). В качестве альтернативы вы можете сгенерировать пользовательский поток потоков, чтобы уменьшить некоторые накладные расходы и т. Д. Построение потока в первую очередь также не является недорогим предприятием.
Пит
6
@Pete: Как только вы начнете беспокоиться о том, что быстрее, вы захотите взглянуть на stackoverflow.com/questions/4351371/…
Бен Фойгт,
20
Обратите внимание, что itoa () не является частью стандарта, и поэтому его использование делает ваш код непереносимым, так как не все компиляторы поддерживают его. Для Linux вы наверняка отсутствуют, если вы не используете что-то еще, кроме GCC, который не поддерживает эту функцию. Если у вас есть C ++ 0x, используйте то, что @Matthieu предложил в своем ответе. Если это не так, используйте stringstream, поскольку это хорошо поддерживаемая функция, и ваш код должен быть совместим с любым компилятором C ++. В качестве альтернативы вы всегда можете использовать sprintf ().
rbaleksandar

Ответы:

2102

C ++ 11 вводит std::stoi(и варианты для каждого числового типа) и std::to_string, аналоги C atoiи, itoaно выражается через std::string.

#include <string> 

std::string s = std::to_string(42);

поэтому я думаю о кратчайшем пути. Вы даже можете опустить наименование типа, используя autoключевое слово:

auto s = std::to_string(42);

Примечание: см. [String.conversions] ( 21,5 в n3242 )

Матье М.
источник
199
to_stringне участник stdисправления: stackoverflow.com/questions/12975341/…
Бен
36
Или, в зависимости от вашего компилятора, просто установите правильный языковой стандарт:g++ -std=c++11 someFile.cc
Thomas M. DuBuisson
12
@Steve: так и должно быть. Он входит stdв каждый известный мне компилятор, кроме одного.
Mooing Duck
5
@Matthiew M. Я использую то же, что вы предлагаете, но я получаю эту ошибку: Error : No instance of overloaded function "std::to_string" matches the argument list я использую VS2010 c ++
19
@Flying: в VS2010 вы должны явно преобразовать целое число к одному из следующих типов [_Longlong, _ULonglong, long double]; т.е.:string s = to_string((_ULonglong)i);
Зак
184

Пару лет спустя, начав дискуссию с @ v.oddou, C ++ 17 наконец-то предоставил способ сделать изначально основанное на макросах решение, не зависящее от типа (сохранено ниже), не проходя через безобразие макросов.

// variadic template
template < typename... Args >
std::string sstr( Args &&... args )
{
    std::ostringstream sstr;
    // fold expression
    ( sstr << std::dec << ... << args );
    return sstr.str();
}

Применение:

int i = 42;
std::string s = sstr( "i is: ", i );
puts( sstr( i ).c_str() );

Foo x( 42 );
throw std::runtime_error( sstr( "Foo is '", x, "', i is ", i ) );

Оригинальный ответ:

Поскольку «преобразование ... в строку» является повторяющейся проблемой, я всегда определяю макрос SSTR () в центральном заголовке моих источников C ++:

#include <sstream>

#define SSTR( x ) static_cast< std::ostringstream & >( \
        ( std::ostringstream() << std::dec << x ) ).str()

Использование настолько просто, насколько это возможно:

int i = 42;
std::string s = SSTR( "i is: " << i );
puts( SSTR( i ).c_str() );

Foo x( 42 );
throw std::runtime_error( SSTR( "Foo is '" << x << "', i is " << i ) );

Вышесказанное совместимо с C ++ 98 (если вы не можете использовать C ++ 11 std::to_string) и не требует никаких сторонних включений (если вы не можете использовать Boost lexical_cast<>); оба эти решения имеют лучшую производительность.

DevSolar
источник
2
Я не очень знаком с, dynamic_castно я использую Clang для компиляции, поэтому он жалуется на это. Если я просто опущу, dynamic_castто это прекрасно скомпилируется; какой цели dynamic_castслужит в этом случае? Мы уже создаем ostringstream, так зачем его кастовать?
Мэтью
2
@ Mathew: ссылка в моем ответе приводит к подробному описанию каждой части конструкции. В то время как мы создалиostringstream , мы позвонили operator<<()на него, который возвращается ostream &- для которых .str()не определен. Мне действительно интересно, как clang сделал бы эту работу без приведения (или почему он генерирует ошибку с ним). Эта конструкция публикуется во многих местах, и я уже более десяти лет использую ее на разных компиляторах, в том числе MSVC, GCC и XLC, поэтому я довольно удивлен, что ее не устраивает.
DevSolar
5
Просто пришли на вечеринку из любопытства и понизили голос. Причина: слишком много голосов за решение, которое не элегантно и, вероятно, медленно. 1. использование макроса. Я систематически не осуждаю какой-либо макрос, но этот слишком короткий, и конечные клиенты всегда боятся повторения аргумента, в дополнение к страху за незащищенные многоканальные макросы. (не защищено do {} while (0)) 2. dynamic_cast. похоже, вам нужен только static_cast, если вы не хотите утверждать, что библиотека действительно реализована так, как вы надеетесь. в этом случае вы должны использовать boost :: polymorphic_downcast вместо этого.
v.oddou
2
@ v.oddou: Вы можете критиковать, конечно. Но 1. недопустим - макрос является одним оператором, do { } while( 0 )ничего бы не добавил. С 2. и 3. Вы, вероятно, получили точку зрения - это можно сделать с помощью статического приведения, и, возможно, один из ваших мастеров шаблонов мог бы придумать «более приятный» интерфейс. Но, как я уже сказал, это ни в коем случае не выдумка меня самого. Посмотрите вокруг, этот макрос (макрос!) Довольно вездесущ. Это случай ПОЛА сам по себе. Я мог бы немного поиграть с этим, чтобы сделать его более «обтекаемым».
DevSolar
1
@ v.oddou: Посмотрите, что я нашел среди вещей, которые принес нам C ++ 17. :-) Надеюсь, вам понравился обновленный ответ.
DevSolar
109

Я обычно использую следующий метод:

#include <sstream>

template <typename T>
  std::string NumberToString ( T Number )
  {
     std::ostringstream ss;
     ss << Number;
     return ss.str();
  }

Это подробно описано здесь .

Расул
источник
2
Перед использованием ssвам нужно ss.clear()это. Я видел неожиданные результаты без этой инициализации.
спасательный круг
14
@lifebalance: я никогда не видел такого поведения.
Расул
18
@lifebalance: Вам не нужен clear()вновь созданный ostringstreamобъект. clear()сбрасывает флаги error / eof, и еще не было сгенерировано ни одного условия error / eof.
Реми Лебо
2
@Rasoul NumberToString(23213.123)производит, 23213.1а std::to_string(23213.123)производит. 23213.123000Что там происходит?
Killzone Kid
1
@KillzoneKid Это потому, что std 'ostream имеют состояние (это означает, что любое предыдущее изменение состояния сохраняется, например, число десятичных цифр), в то время как этот метод начинается с состояния по умолчанию.
xryl669
85

Вероятно, наиболее распространенный простой способ - это, по сути, ваш второй выбор в шаблон с именем lexical_cast, например, в Boost , поэтому ваш код выглядит следующим образом:

int a = 10;
string s = lexical_cast<string>(a);

Одним из достоинств этого является то, что он поддерживает и другие приведения (например, в противоположном направлении работает так же хорошо).

Также обратите внимание, что хотя Boost lexical_cast изначально начинался с простой записи в поток строк, а затем извлекался из потока, теперь у него есть пара дополнений. Прежде всего, были добавлены специализации для нескольких типов, поэтому для многих распространенных типов это существенно быстрее, чем использование stringstream. Во-вторых, теперь он проверяет результат, поэтому (например), если вы преобразуете строку в переменную int, она может выдать исключение, если строка содержит что-то, что не может быть преобразовано в int(например, 1234успешно выполнится , но123abc сгенерирует) ,

Начиная с C ++ 11, есть std::to_stringфункция, перегруженная для целочисленных типов, поэтому вы можете использовать такой код:

int a = 20;
std::string s = std::to_string(a);
// or: auto s = std::to_string(a);

Стандарт определяет их как эквивалентное выполнению преобразования sprintf(с использованием спецификатора преобразования, который соответствует предоставленному типу объекта, например, %dfor int), в буфер достаточного размера, а затем создание std::stringсодержимого этого буфера.

Джерри Гроб
источник
2
Хорошо, я предпочитаю ответ Кевина, хотя он показывает include и пространство имен. Просто незначительный захват. :) Хорошая работа, хотя!
Джейсон Р. Мик
4
Я бы сказал, что это тот путь, если у вас нет поддержки C ++ 11.
Алекс
40

Если у вас установлен Boost (что вам и нужно):

#include <boost/lexical_cast.hpp>

int num = 4;
std::string str = boost::lexical_cast<std::string>(num);
Kevin
источник
4
Договорились об установке буста. Я думаю, что более часто можно было бы отформатировать строку. Для этой цели я предпочитаю boost :: format например format ("% 02d", number) .str ()
Werner Erasmus
28

Было бы проще использовать stringstreams:

#include <sstream>

int x = 42;          // The integer
string str;          // The string
ostringstream temp;  // 'temp' as in temporary
temp << x;
str = temp.str();    // str is 'temp' as string

Или сделайте функцию:

#include <sstream>

string IntToString(int a)
{
    ostringstream temp;
    temp << a;
    return temp.str();
}
user2287915
источник
18

Не то, что я знаю, в чистом C ++. Но небольшая модификация того, что вы упомянули

string s = string(itoa(a));

должно работать, и это довольно коротко.

user541686
источник
55
itoa()не является стандартной функцией!
карикатурист
4
@cartoonist: Тогда что это?
user541686
20
Эта функция не определена в ANSI-C и C ++. Так что это не поддерживается некоторым компилятором, таким как g ++.
карикатурист
17

Вы можете использовать std::to_stringдоступные в C ++ 11, как предложено Matthieu M .:

std::to_string(42);

Или, если производительность имеет решающее значение (например, если вы делаете много переходов), вы можете использовать fmt::format_intс {} FMT библиотеки преобразовать целое число std::string:

fmt::format_int(42).str();

Или строка C:

fmt::format_int f(42);
f.c_str();

Последний не выполняет динамического выделения памяти и более чем в 10 раз быстрее, чем std::to_stringв тестах Boost Karma. См. Быстрое преобразование целых чисел в строки в C ++ для получения дополнительной информации.

Обратите внимание, что оба потока потокобезопасны.

В отличие от std::to_string,fmt::format_int не требует C ++ 11 и работает с любым компилятором C ++.

Отказ от ответственности: я являюсь автором библиотеки {fmt}.

Витовт
источник
2
Мне было любопытно, что у меня нет динамического выделения памяти, хотя он остается потокобезопасным (повторно входящим), поэтому я прочитал ваш код - c_str()возвращает указатель на буфер, объявленный внутри fmt::FormatIntкласса - поэтому возвращенный указатель будет недействительным при точка с запятой - см. также stackoverflow.com/ru/questions/4214153/lifetime-of-temporaries
Сорен
1
Да, такое же поведение, как и с std::string::c_str()(таким образом, именование). Если вы хотите использовать его вне полного выражения, создайте объект. FormatInt f(42);Тогда вы можете использовать его f.c_str()без опасности его уничтожения.
Витаут
1
Я получаю что-то странное, когда пытаюсь преобразовать int в строку, используя std :: to_string (num). Если я сохраню результат в переменной и попытаюсь получить к нему доступ как stringNum [1] или stringNum [n] при увеличении n, я получаю мусор.
user8951490
1
Это, безусловно, правильный ответ на этот вопрос: эффективный и стандартный код без учета состояния.
xryl669
16

sprintf()довольно хорошо для преобразования формата. Затем вы можете назначить полученную строку C строке C ++, как вы это делали в 1.

Throwback1986
источник
1
Хех да Тем не менее, я обычно полагаюсь на snprintf () и друзей, когда дело касается строк C.
Throwback1986
1
@MatthieuM. Ваш комментарий далее доказывает, что вы не. Если выходные данные были усечены из-за этого ограничения, тогда возвращаемое значение - это количество символов (исключая завершающий нулевой байт), которое было бы записано в последнюю строку, если бы было достаточно места. Таким образом, возвращаемое значение размера или более означает, что вывод был усечен. Таким образом, вы называете его с NULLнулевым размером, чтобы получить необходимый размер буфера.
user1095108
2
@ user1095108: Я думаю, что вы ошибаетесь snprintf(обратите внимание на префикс SNP ) и sprintf(обратите внимание на префикс SP ). Вы передаете размер первому, и он заботится о том, чтобы не переполниться, однако последний не знает размер буфера и, таким образом, может переполниться.
Матье М.
1
Идея состоит в том, чтобы snprintfсначала назвать вариант, а затем sprintfвариант. Поскольку размер буфера уже известен, вызов sprintfстановится полностью безопасным.
user1095108
1
@ user1095108 Ах, да. Если первого буфера для snprintf недостаточно, возвращаемое значение говорит вам, что будет достаточно. Я все еще использовал бы snprintf для второго вызова, потому что полагаться на реализации sprintf и snprintf для сравнения неоправданно опасно.
Мабрахам
11

Сначала включите:

#include <string>
#include <sstream>

Второй добавить метод:

template <typename T>
string NumberToString(T pNumber)
{
 ostringstream oOStrStream;
 oOStrStream << pNumber;
 return oOStrStream.str();
}

Используйте метод как это:

NumberToString(69);

или

int x = 69;
string vStr = NumberToString(x) + " Hello word!."
Alex
источник
10

Использование stringstream для преобразования чисел опасно!

См. Http://www.cplusplus.com/reference/ostream/ostream/operator%3C%3C/, где рассказывается, что operator<<вставляет форматированный вывод.

В зависимости от текущей локали целое число, превышающее 3 цифры, может быть преобразовано в строку из 4 цифр с добавлением дополнительного разделителя тысяч.

Например, int = 1000 может быть преобразован в строку 1.001. Это может привести к тому, что операции сравнения вообще не будут работать.

Поэтому я настоятельно рекомендую использовать std::to_string способ. Это проще и делает то, что вы ожидаете.

Обновлено (см. Комментарии ниже) :

C ++ 17 предоставляет std::to_charsв качестве высокопроизводительной независимой от локали альтернативы

YesThatIsMyName
источник
2
Я согласен, что это серьезная проблема, если вам нужно обмениваться данными. К сожалению, также std::to_stringиспользуется текущая локаль (см. En.cppreference.com/w/cpp/string/basic_string/to_string , раздел «Примечания»). Почти все стандартные инструменты (от строковых потоков до sprintf, но также и sscanfт. Д.) Используют текущую локаль. Я не знал об этом до недавнего времени, когда это сильно ударило меня. В настоящее время используют домашние вещи, не трудно сделать.
Берт Бриль,
В приведенной выше ссылке также указано, что C ++ 17 предоставляет std :: to_chars в качестве высокопроизводительной независимой от локали альтернативы.
YesThatIsMyName
К сожалению, я застрял с C ++ 11 на предстоящий год (а), к счастью, уже довольно неплохо).
Берт Бриль
1
from_chars и to_chars были бы идеальными, но, к сожалению, они не предлагали вариант wchar_t.
gast128
8

Для C ++ 98 есть несколько вариантов:

boost/lexical_cast

Boost не является частью библиотеки C ++, но содержит много полезных расширений библиотеки.

lexical_castШаблон функции предлагает удобную и последовательную форму для поддержки общих преобразований в и из произвольных типов , когда они представлены в виде текста.
- Документация Boost

#include "boost/lexical_cast.hpp"
#include <string>

int main() {
    int x = 5;
    std::string x_str = boost::lexical_cast<std::string>(x);
    return 0;
}

Что касается времени выполнения, lexical_castоперация занимает около 80 микросекунд (на моей машине) при первом преобразовании, а затем значительно ускоряется, если выполняется избыточно.


itoa

Эта функция не определена в ANSI-C и не является частью C ++, но поддерживается некоторыми компиляторами.
- cplusplus.com

Это означает, что gcc/ g++не может скомпилировать код, используя itoa.

#include <stdlib.h>

int main() {
    int x = 5;
    char * x_str = new char[2];
    x_str = itoa(x, x_str, 10); // base 10
    return 0;
}

Нет времени выполнения, чтобы сообщить. У меня не установлена ​​Visual Studio, которая, как сообщается, может компилироваться itoa.


sprintf

sprintf является стандартной библиотечной функцией C, которая работает со строками C и является вполне допустимой альтернативой.

Составляет строку с тем же текстом, который будет напечатан, если формат был использован в printf, но вместо печати содержимое сохраняется в виде строки C в буфере, указанном str.
- cplusplus.com

#include <stdio.h>

int main() {
    int x = 5;
    char * x_str = new char[2];
    int chars_written = sprintf(x_str, "%d", x);
    return 0;
}

stdio.hЗаголовок не может быть необходимым. Что касается времени выполнения, sprintfоперация занимает около 40 микросекунд (на моей машине) при первом преобразовании, а затем значительно ускоряется, если выполняется избыточно.


stringstream

Это основной способ преобразования целых чисел в строки библиотеки C ++ и наоборот. Существуют аналогичные родственные функции, stringstreamкоторые дополнительно ограничивают предполагаемое использование потока, например ostringstream. Использование, в ostringstreamчастности, говорит читателю вашего кода, что вы <<, по сути, собираетесь использовать только оператор. Эта функция - все, что особенно необходимо для преобразования целого числа в строку. Смотрите этот вопрос для более детального обсуждения.

#include <sstream>
#include <string>

int main() {
    int x = 5;
    std::ostringstream stream;
    stream << x;
    std::string x_str = stream.str();
    return 0;
}

Что касается времени выполнения, ostringstreamоперация занимает около 71 микросекунды (на моей машине), а затем значительно ускоряется, если выполняется избыточно, но не настолько, как предыдущие функции .


Конечно, есть и другие варианты, и вы можете даже включить один из них в свои собственные функции, но это предлагает аналитический взгляд на некоторые из популярных.

Джошуа Детвилер
источник
Спасибо за заботу о нас (пользователи C ++ 98)
A. B
@AB Я не могу поверить, что все еще есть пользователи C ++ 98.
Котаускас
@VladislavToncharov Когда ваша работа заключается исключительно в поддержке устаревшего оборудования и кода, вы отбрасываете старые вещи, используя более свежие отраслевые стандарты. Летом назад я писал код на Python 2.3.
Джошуа
@JoshuaDetwiler О, забыл об этом, извините.
Котаускас
4

C ++ 17 предоставляет std :: to_chars в качестве высокопроизводительной независимой от локали альтернативы.


источник
3

Довольно просто добавить синтаксический сахар, который позволяет составлять строки на лету, как поток

#include <string>
#include <sstream>

struct strmake {
    std::stringstream s;
    template <typename T> strmake& operator << (const T& x) {
        s << x; return *this;
    }   
    operator std::string() {return s.str();}
};

Теперь вы можете добавлять все, что хотите (при условии, что << (std::ostream& ..)для него определен оператор ), strmake()и использовать его вместоstd::string .

Пример:

#include <iostream>

int main() {
    std::string x =
      strmake() << "Current time is " << 5+5 << ":" << 5*5 << " GST";
    std::cout << x << std::endl;
}
АндрейС Щербаков
источник
2

Редактируется. Если вам нужно быстрое преобразование целого числа с фиксированным числом цифр в символ *, дополненное слева до '0' , это пример для архитектуры с прямым порядком байтов (все x86, x86_64 и другие):

Если вы конвертируете двузначное число:

int32_t s = 0x3030 | (n/10) | (n%10) << 8;

Если вы конвертируете трехзначное число:

int32_t s = 0x303030 | (n/100) | (n/10%10) << 8 | (n%10) << 16;

Если вы конвертируете четырехзначное число:

int64_t s = 0x30303030 | (n/1000) | (n/100%10)<<8 | (n/10%10)<<16 | (n%10)<<24;

И так далее до семизначных чисел. В этом примере nзадано целое число. После преобразования его строковое представление может быть доступно как (char*)&s:

std::cout << (char*)&s << std::endl;

ПРИМЕЧАНИЕ. Если вам нужен порядок байтов с прямым порядком байтов, хотя я не проверял его, но вот пример: для трехзначного числа это int32_t s = 0x00303030 | (n/100)<< 24 | (n/10%10)<<16 | (n%10)<<8;для четырехзначных чисел (64-разрядная арка): int64_t s = 0x0000000030303030 | (n/1000)<<56 | (n/100%10)<<48 | (n/10%10)<<40 | (n%10)<<32;я думаю, что это должно работать.

Alek
источник
2
Как насчет порядка байтов?
Шефф
Разве это не неопределенное поведение из-за псевдонимов указателей?
dgnuff
1
@shjeff спасибо за комментарий, я добавил примечание по порядку байтов в ответ.
Алек
@dgnuff спасибо за указание на это, хотя у меня не было проблем с этим, вы правы. Я немного изменил ответ, чтобы он соответствовал строгим правилам алиасинга, спасибо.
Алек
1

Использование:

#define convertToString(x) #x

int main()
{
    convertToString(42); // Returns const char* equivalent of 42
}
maverick9888
источник
3
Работает только с литеральными числами, не оценивает переменное содержимое, хотя иногда полезно.
Волк,
Правильно. Но определенно удобно в то время
maverick9888
1
Работает только во время компиляции с литеральными числами констант, я думаю, что OP запрашивает динамическое преобразование, используя переменные целые числа
Ing. Херардо Санчес
0

Я использую:

int myint = 0;
long double myLD = 0.0;

string myint_str = static_cast<ostringstream*>(&(ostringstream() << myint))->str();
string myLD_str = static_cast<ostringstream*>(&(ostringstream() << myLD))->str();

Это работает на моих Windows и Linux G ++ компиляторах.

J_C
источник
0

Вот еще один простой способ сделать

char str[100];
sprintf(str, "%d", 101);
string s = str;

sprintf хорошо известен для вставки любых данных в строку требуемого формата.

Вы можете преобразовать char *массив в строку, как показано в третьей строке.

Натеш бхат
источник
0

Это сработало для меня -

Мой код:

#include <iostream>
using namespace std;

int main()
{
    int n = 32;
    string s = to_string(n);
    cout << "string: " + s  << endl;
    return 0;
}
Гонсало Гарридо
источник
По существу, используя что? stringstream?
Питер Мортенсен
@PeterMortensen Посмотрите внимательно, этоstd::to_string()
Kotauskas
у меня есть using namespace std;:)
Гонсалу Гарридо
0

C ++ 11 введен std::to_string()для числовых типов:

int n = 123; // Input, signed/unsigned short/int/long/long long/float/double
std::string str = std::to_string(n); // Output, std::string
Камруджаман Радость
источник
4
Привет! Не могли бы вы добавить объяснение, почему и как это дает ответ на вопрос?
другой узел
0

Использование:

#include<iostream>
#include<string>

std::string intToString(int num);

int main()
{
    int integer = 4782151;

    std::string integerAsStr = intToString(integer);

    std::cout << "integer = " << integer << std::endl;
    std::cout << "integerAsStr = " << integerAsStr << std::endl;

    return 0;
}

std::string intToString(int num)
{
    std::string numAsStr;

    while (num)
    {
        char toInsert = (num % 10) + 48;
        numAsStr.insert(0, 1, toInsert);

        num /= 10;
    }
    return numAsStr;
}
Тайяб Мажар
источник
1
Полностью терпит неудачу для n≤0
Тоби Спейт
-1
string number_to_string(int x) {

    if (!x)
        return "0";

    string s, s2;
    while(x) {
        s.push_back(x%10 + '0');
        x /= 10;
    }
    reverse(s.begin(), s.end());
    return s;
}
Абдулла Абдельмонем
источник
1
Спасибо за этот фрагмент кода, который может предоставить некоторую ограниченную краткосрочную помощь. Правильное объяснение значительно улучшило бы его долгосрочную ценность, показав, почему это хорошее решение проблемы, и сделало бы его более полезным для будущих читателей с другими, похожими вопросами. Пожалуйста, измените свой ответ, чтобы добавить некоторые объяснения, в том числе предположения, которые вы сделали.
Тоби Спейт
Полностью терпит неудачу для n≤0
Тоби Спейт
Добавьте комментарии, объясните свой ответ, прочитайте, как ответить .
Аксен Р
-1

Если вы используете MFC , вы можете использовать CString:

int a = 10;
CString strA;
strA.Format("%d", a);
Tur1ng
источник
8
Следует отметить, что это расширение только для Microsoft: msdn.microsoft.com/en-us/library/ms174288.aspx
JonnyJD
1
Мне нравится идея CString :: Format (). К сожалению, это не переносимая только MS.
Ник
1
Я обновил свой ответ, включив в него информацию из вашего комментария @JonnyJD, так как 5 лет спустя я продолжаю опускаться за него ..
Tur1ng
-2
char * bufSecs = new char[32];
char * bufMs = new char[32];
sprintf(bufSecs, "%d", timeStart.elapsed()/1000);
sprintf(bufMs, "%d", timeStart.elapsed()%1000);
user2047065
источник
12
утечки памяти, -1 от меня
Пол
Это пахнет как переполнение буфера.
Котаускас
-2
namespace std
{
    inline string to_string(int _Val)
    {   // Convert long long to string
        char _Buf[2 * _MAX_INT_DIG];
        snprintf(_Buf, "%d", _Val);
        return (string(_Buf));
    }
}

Теперь вы можете использовать to_string(5).

Питер Мортенсен
источник
10
Хотя это решение работает, оно крайне не рекомендуется! Имена, начинающиеся с подчеркивания и заглавной буквы, зарезервированы для компилятора, вы никогда не должны их использовать. Внедрение функций в stdпространство имен - это тоже не то, что вы должны делать. Кроме того, это не похоже _MAX_INT_DIGна стандартный макрос, поэтому, если он определен неправильно, этот код обладает большим потенциалом вызывать неопределенное поведение. -1
iFreilicht
6
Что такое _MAX_INT_DIG и почему оно удвоено?
Пол
-2

Я думаю, что использовать stringstreamдовольно просто:

 string toString(int n)
 {
     stringstream ss(n);
     ss << n;
     return ss.str();
 }

 int main()
 {
    int n;
    cin >> n;
    cout << toString(n) << endl;
    return 0;
 }
rashedcs
источник
Это было упомянуто в вопросе, и, к сожалению, довольно медленно.
Котаускас
-3

Вы используете тип счетчика алгоритма для преобразования в строку. Я получил эту технику от программирования компьютеров Commodore 64 . Это также хорошо для программирования игр.

  • Вы берете целое число и берете каждую цифру, которая взвешена на степени 10. Поэтому предположим, что целое число равно 950.

    • Если целое число равно или больше 100 000, то вычтите 100 000 и увеличьте счетчик в строке на ["000000"];
      продолжайте делать это до тех пор, пока в позиции 100 000 больше не останется цифр. Отбросьте еще одну степень десяти.

    • Если целое число равно или больше 10000, то вычтите 10000 и увеличьте счетчик в строке на ["000000"] + 1 позиция;
      продолжайте делать это до тех пор, пока не останется цифр в позиции 10000.

  • Отбросьте еще одну степень десяти

  • Повторите шаблон

Я знаю, что 950 слишком мал для использования в качестве примера, но я надеюсь, что вы поняли идею.

AdmiralSmith
источник
Не очень полезно описывать алгоритм, а не показывать пример в коде.
cdeerinck