c++ - separar - salida con formato en c
c++: ¿Número de formato con comas? (7)
Quiero escribir un método que tome un entero y devuelva una std::string
de ese entero formateado con comas.
Declaración de ejemplo:
std::string FormatWithCommas(long value);
Ejemplo de uso:
std::string result = FormatWithCommas(7800);
std::string result2 = FormatWithCommas(5100100);
std::string result3 = FormatWithCommas(201234567890);
// result = "7,800"
// result2 = "5,100,100"
// result3 = "201,234,567,890"
¿Cuál es la forma en C ++ de formatear un número como una string
con comas?
(La bonificación sería manejar double
s también).
Considero que la siguiente respuesta es más fácil que las demás:
string numWithCommas = to_string(value);
int insertPosition = numWithCommas.length() - 3;
while (insertPosition > 0) {
numWithCommas.insert(insertPosition, ",");
insertPosition-=3;
}
Esto insertará comas rápida y correctamente en su cadena de dígitos.
Esta es una escuela muy antigua, la uso en bucles grandes para evitar la creación de instancias de otro búfer de cadenas.
void tocout(long a)
{
long c = 1;
if(a<0) {a*=-1;cout<<"-";}
while((c*=1000)<a);
while(c>1)
{
int t = (a%c)/(c/1000);
cout << (((c>a)||(t>99))?"":((t>9)?"0":"00")) << t;
cout << (((c/=1000)==1)?"":",");
}
}
Para hacerlo más flexible, podría construir la faceta con una cadena de miles de miles y agrupación personalizada. De esta forma puede configurarlo en tiempo de ejecución.
#include <locale>
#include <iostream>
#include <iomanip>
#include <string>
class comma_numpunct : public std::numpunct<char>
{
public:
comma_numpunct(char thousands_sep, const char* grouping)
:m_thousands_sep(thousands_sep),
m_grouping(grouping){}
protected:
char do_thousands_sep() const{return m_thousands_sep;}
std::string do_grouping() const {return m_grouping;}
private:
char m_thousands_sep;
std::string m_grouping;
};
int main()
{
std::locale comma_locale(std::locale(), new comma_numpunct('','', "/03"));
std::cout.imbue(comma_locale);
std::cout << std::setprecision(2) << std::fixed << 1000000.1234;
}
Puedes hacer lo que Jacob sugirió e imbue
con la configuración regional ""
, pero usará el sistema predeterminado, lo que no garantiza que obtengas la coma. Si desea forzar la coma (independientemente de la configuración regional predeterminada del sistema), puede hacerlo proporcionándole su propia faceta numpunct
. Por ejemplo:
#include <locale>
#include <iostream>
#include <iomanip>
class comma_numpunct : public std::numpunct<char>
{
protected:
virtual char do_thousands_sep() const
{
return '','';
}
virtual std::string do_grouping() const
{
return "/03";
}
};
int main()
{
// this creates a new locale based on the current application default
// (which is either the one given on startup, but can be overriden with
// std::locale::global) - then extends it with an extra facet that
// controls numeric output.
std::locale comma_locale(std::locale(), new comma_numpunct());
// tell cout to use our new locale.
std::cout.imbue(comma_locale);
std::cout << std::setprecision(2) << std::fixed << 1000000.1234;
}
Si está utilizando Qt, puede usar este código:
const QLocale & cLocale = QLocale::c();
QString resultString = cLocale.toString(number);
Además, no olvide agregar #include <QLocale>
.
Utilice std::locale
con std::stringstream
#include <iomanip>
#include <locale>
template<class T>
std::string FormatWithCommas(T value)
{
std::stringstream ss;
ss.imbue(std::locale(""));
ss << std::fixed << value;
return ss.str();
}
Descargo de responsabilidad: la portabilidad podría ser un problema y probablemente debería ver qué configuración regional se usa cuando se pasa ""
basado en las respuestas anteriores, terminé con este código:
#include <iomanip>
#include <locale>
template<class T>
std::string numberFormatWithCommas(T value){
struct Numpunct: public std::numpunct<char>{
protected:
virtual char do_thousands_sep() const{return '','';}
virtual std::string do_grouping() const{return "/03";}
};
std::stringstream ss;
ss.imbue({std::locale(), new Numpunct});
ss << std::setprecision(2) << std::fixed << value;
return ss.str();
}