Konwersja int do std :: string

143

Jaki jest najkrótszy sposób, najlepiej wbudowany, aby przekonwertować int na łańcuch? Odpowiedzi za pomocą STL i Boost będą mile widziane.

Amir Rachum
źródło
63
W C ++ 11 możesz użyć to_stringlikestd::string s = std::to_string(42)
5
Niech żyje C ++ 11 i to_string! :)
augustin

Odpowiedzi:

351

Możesz użyć std :: to_string w C ++ 11

int i = 3;
std::string str = std::to_string(i);
Yochai Timmer
źródło
4
std :: to_string () nie działa w MinGW, jeśli kogoś to obchodzi.
Archie
3
@bparker Zgadza się, to chyba zostało naprawione w gcc 4.8.0. MinGW z najnowszym Code :: Blocks (13.12) nadal ma gcc 4.7.1.
Archie
47
#include <sstream>
#include <string>
const int i = 3;
std::ostringstream s;
s << i;
const std::string i_as_string(s.str());
Benoit
źródło
36

boost::lexical_cast<std::string>(yourint) z boost/lexical_cast.hpp

Działa na wszystko dzięki obsłudze std :: ostream, ale nie jest tak szybka, jak na przykład itoa

Wydaje się nawet, że jest szybszy niż stringstream lub scanf:

ltjax
źródło
15
Boost jest twoim przyjacielem, jeśli nie było prostego sposobu na zrobienie tego w Standard C ++ ... Oczywiście podoba mi się to lexical_cast, co przynosi, ale czuję, że Boost jest dość przesadą dla tego rodzaju zadań ...
rubenvb
2
Overkill? Na podstawie czego? boost.org/doc/libs/1_53_0/doc/html/boost_lexical_cast/…
Catskul
Należy wziąć pod uwagę swoich odbiorców, jeśli nie mogą korzystać z funkcji Boost
Damian
5
„Odpowiedzi używające STL i Boost będą mile widziane”. - Uwzględniona publiczność
Conrad Jones
30

Dobrze znanym sposobem na to jest użycie operatora strumienia:

#include <sstream>

std::ostringstream s;
int i;

s << i;

std::string converted(s.str());

Oczywiście możesz uogólnić to dla dowolnego typu używając funkcji szablonu ^^

#include <sstream>

template<typename T>
std::string toString(const T& value)
{
    std::ostringstream oss;
    oss << value;
    return oss.str();
}
neuro-
źródło
1
Uwaga: to wymaga #include <sstream>.
TechNyquist
@TechNyquist: Masz rację. Nie miał być kompilowalny, ale zmieniony!
neuro-
1
Więc nie chciałeś, żeby było to kompilowalne, ale tak naprawdę z dołączeniem jest :)
TechNyquist.
1
@TechNyquist: Tak, z niektórymi std::;)
neuro
16

Jeśli nie możesz używać std::to_stringz C ++ 11, możesz napisać to tak, jak jest zdefiniowane na cppreference.com:

std::string to_string( int value ) Przekształca podpisane całkowitą dziesiętną na sznurku z tej samej treści jak co std::sprintf(buf, "%d", value)przyniosłoby dla dostatecznie dużych buf.

Realizacja

#include <cstdio>
#include <string>
#include <cassert>

std::string to_string( int x ) {
  int length = snprintf( NULL, 0, "%d", x );
  assert( length >= 0 );
  char* buf = new char[length + 1];
  snprintf( buf, length + 1, "%d", x );
  std::string str( buf );
  delete[] buf;
  return str;
}

Możesz z tym zrobić więcej. Po prostu użyj "%g"do konwersji float lub double na string, użyj "%x"do konwersji int na reprezentację szesnastkową i tak dalej.

user2622016
źródło
14

Niestandardowa funkcja, ale jest zaimplementowana w większości popularnych kompilatorów:

int input = MY_VALUE;
char buffer[100] = {0};
int number_base = 10;
std::string output = itoa(input, buffer, number_base);

Aktualizacja

C ++ 11 wprowadził kilka std::to_stringprzeciążeń (zwróć uwagę, że domyślnie jest to base-10).

Zac Howland
źródło
3
@DevSolar: Powinieneś rozwinąć. Podano już przykład wzmocnienia. To rozwiązanie jest dostępne w większości kompilatorów, gdy boost nie jest zainstalowany (lub twoje wymagania zabraniają używania go z jakiegokolwiek powodu). Te ostreamprace, jak również, aż trzeba zapisać numer ciąg jako coś innego niż binarny, ósemkowy, lub w formacie szesnastkowym (np base-32).
Zac Howland,
3
Nie podoba mi się, gdy niestandardowe funkcje lubią itoa()lub stricmp()są podawane jako odpowiedź na cokolwiek .
DevSolar
6
Przepraszam, że uraziłem twoją wrażliwość, ale powiedziałem, że to niestandardowa funkcja w pierwszym zdaniu. Nie wspomniałem o tym, ale sprintfmogę również osiągnąć cel PO (chociaż nadal cierpi z powodu braku elastyczności, jeśli potrzebne jest coś innego niż wspólne liczby podstawowe).
Zac Howland,
1
Tak, powiedziałeś to, a ja nie przegłosowałem Twojej odpowiedzi, nawet jeśli bardzo mnie to nie chciało. Więc myślę, że jesteśmy kwita. ;-)
DevSolar
8

Poniższe makro nie jest tak kompaktowe, jak jednorazowe ostringstreamlubboost::lexical_cast .

Ale jeśli potrzebujesz wielokrotnie konwersji na ciąg w swoim kodzie, to makro jest bardziej eleganckie w użyciu niż bezpośrednia obsługa strumieni ciągów lub jawne rzutowanie za każdym razem.

Jest również bardzo wszechstronny, ponieważ konwertuje wszystko, co jest obsługiwane operator<<(), nawet w połączeniu.

Definicja:

#include <sstream>

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

Wyjaśnienie:

Jest std::decto sposób na przekształcenie anonimowości ostringstreamw rodzaj ogólny, wolny od skutków ubocznych, ostreamdzięki czemu operator<<()wyszukiwanie funkcji działa poprawnie dla wszystkich typów. (W przeciwnym razie będziesz miał kłopoty, jeśli pierwszy argument jest typem wskaźnikowym.)

dynamic_castZwraca wpisać plecami do ostringstreamtak można wywołać str()na nim.

Posługiwać się:

#include <string>

int main()
{
    int i = 42;
    std::string s1 = SSTR( i );

    int x = 23;
    std::string s2 = SSTR( "i: " << i << ", x: " << x );
    return 0;
}
DevSolar
źródło
1
@rubenvb: Powiedz mi, jak zamienić to w szablon, a ja zaktualizuję wszystkie projekty C ++, w których
używałem
@rubenvb: Przepraszamy, to nie było tak jasne, jak powinno. Nie widzę sposobu, w jaki sposób mógłbym przekształcić to w szablon (używając C ++ 98) bez utraty możliwości łączenia łańcuchowego danych wyjściowych (jak w moim drugim przykładzie) lub konieczności wymyślenia zawiłego bałaganu do obsługi dowolna liczba parametrów i typów parametrów.
DevSolar,
@DevSolar: nie inline template<class T> std::string SSTR( T x ) { return dynamic_cast< std::ostringstream & >( (std::ostringstream() << std::dec << x) ).str() }zrobiłbyś? (Nie testowałem, ale zastanawiam się, co poszłoby nie tak i dlaczego?
rubenvb
@rubenvb: Zrobiłoby to dla osoby int(mój pierwszy przykład). Ale bez ostreamwidoczne dla kompilatora w main(jak to jest ukryty wewnątrz funkcji szablonu), będzie starał się patrzeć operator<<()na const char []moim drugim przykładzie - który będzie rechot. Wiem, że OP wymagał tylko rozszerzenia int, ale to bardziej ogólne makro jest tak przydatne (i właściwie dość rozpowszechnione), że pomyślałem, że umieściłem je tutaj.
DevSolar
Ze względu na wszechstronność preferuję funkcję szablonu. Dla łańcucha łańcuchowego, który może być obsługiwany w tej samej funkcji z odrobiną RTTI ...
neuro
2

Możesz użyć tej funkcji, aby przekonwertować intna std::stringafter w tym <sstream>:

#include <sstream>

string IntToString (int a)
{
    stringstream temp;
    temp<<a;
    return temp.str();
}
dront
źródło
-2
#include <string>
#include <stdlib.h>

Oto kolejny łatwy sposób konwersji int na string

int n = random(65,90);
std::string str1=(__String::createWithFormat("%c",n)->getCString());

możesz odwiedzić ten link, aby uzyskać więcej metod https://www.geeksforgeeks.org/what-is-the-best-way-in-c-to-convert-a-number-to-a-string/

Vipul Dungranee
źródło
musi zawierać następujące, aby użyć tych plików nagłówka metody #include <string> #include <stdlib.h>
Vipul Dungranee
-3

Przypuśćmy, że tak integer = 0123456789101112. Teraz ta liczba całkowita może zostać przekonwertowana na łańcuch przez stringstreamklasę.

Oto kod w C ++:

   #include <bits/stdc++.h>
   using namespace std;
   int main()
   {
      int n,i;
      string s;
      stringstream st;
      for(i=0;i<=12;i++)
      {
        st<<i;
      }
      s=st.str();
      cout<<s<<endl;
      return 0;

    }
Shawon
źródło
nie były podobne, ale pełniejsze odpowiedzi udzielone już wiele lat temu?
Walter
Tak, ale myślę, że ta odpowiedź jest idealna, ponieważ nie otrzymałem żadnej skutecznej odpowiedzi z poprzedniej.
Shawon