Namespaces
Variants

std::num_put<CharT,OutputIt>:: put, std::num_put<CharT,OutputIt>:: do_put

From cppreference.net
std::num_put
Member functions
num_put::put num_put::do_put
Definido en el encabezado <locale>
(1)
public :

iter_type put ( iter_type out, std:: ios_base & str,

char_type fill, bool val ) const ;
iter_type put ( iter_type out, std:: ios_base & str,
char_type fill, long val ) const ;
iter_type put ( iter_type out, std:: ios_base & str,
char_type fill, long long val ) const ;
(desde C++11)
iter_type put ( iter_type out, std:: ios_base & str,
char_type fill, unsigned long val ) const ;
iter_type put ( iter_type out, std:: ios_base & str,
char_type fill, unsigned long long val ) const ;
(desde C++11)
iter_type put ( iter_type out, std:: ios_base & str,
char_type fill, double val ) const ;
iter_type put ( iter_type out, std:: ios_base & str,
char_type fill, long double val ) const ;
iter_type put ( iter_type out, std:: ios_base & str,
char_type fill, const void * val ) const ;
(2)
protected :

virtual iter_type do_put ( iter_type out, std:: ios_base & str,

char_type fill, bool val ) const ;
virtual iter_type do_put ( iter_type out, std:: ios_base & str,
char_type fill, long val ) const ;
virtual iter_type do_put ( iter_type out, std:: ios_base & str,
char_type fill, long long val ) const ;
(desde C++11)
virtual iter_type do_put ( iter_type out, std:: ios_base & str,
char_type fill, unsigned long val ) const ;
virtual iter_type do_put ( iter_type out, std:: ios_base & str,
char_type fill, unsigned long long val ) const ;
(desde C++11)
virtual iter_type do_put ( iter_type out, std:: ios_base & str,
char_type fill, double val ) const ;
virtual iter_type do_put ( iter_type out, std:: ios_base & str,
char_type fill, long double val ) const ;
virtual iter_type do_put ( iter_type out, std:: ios_base & str,
char_type fill, const void * val ) const ;
1) Función miembro pública, llama a la función miembro virtual protegida do_put de la clase más derivada.
2) Escribe caracteres en la secuencia de salida out que representan el valor de val , formateado según lo solicitado por los indicadores de formato str. flags ( ) y las facetas std::numpunct y std::ctype de la configuración regional imbucida en el flujo str . Esta función es llamada por todos los operadores de flujo de salida formateados, como std:: cout << n ; .

La conversión ocurre en cuatro etapas:

Contenidos

Etapa 1: selección del especificador de conversión

  • Los indicadores de formato de E/S se obtienen, como si fuera mediante
fmtflags basefield = ( str. flags ( ) & std:: ios_base :: basefield ) ;
fmtflags uppercase = ( str. flags ( ) & std:: ios_base :: uppercase ) ;
fmtflags floatfield = ( str. flags ( ) & std:: ios_base :: floatfield ) ;
fmtflags showpos = ( str. flags ( ) & std:: ios_base :: showpos ) ;
fmtflags showbase = ( str. flags ( ) & std:: ios_base :: showbase ) ;
fmtflags showpoint = ( str. flags ( ) & std:: ios_base :: showpoint ) ;
  • Si el tipo de val es bool :
    • Si boolalpha == 0 , entonces convierte val al tipo int y realiza salida de entero.
    • Si boolalpha ! = 0 , obtiene std:: use_facet < std:: numpunct < CharT >> ( str. getloc ( ) ) . truename ( ) si val == true o std:: use_facet < std:: numpunct < CharT >> ( str. getloc ( ) ) . falsename ( ) si val == false , y envía cada carácter sucesivo c de esa cadena a out con * out ++ = c . No se realiza más procesamiento en este caso, la función retorna out .
  • Si el tipo de val es un tipo entero, se selecciona la primera opción aplicable de las siguientes:
    • Si basefield == oct , usará el especificador de conversión % o .
    • Si basefield == hex && ! uppercase , usará el especificador de conversión % x .
    • Si basefield == hex , usará el especificador de conversión % X .
    • Si el tipo de val es con signo, usará el especificador de conversión % d .
    • Si el tipo de val es sin signo, usará el especificador de conversión % u .
  • Para tipos enteros, se añade el modificador de longitud a la especificación de conversión si es necesario: l para long y unsigned long , ll para long long y unsigned long long (desde C++11) .
  • Si el tipo de val es un tipo de punto flotante, se selecciona la primera opción aplicable de las siguientes:
(hasta C++11)
(desde C++11)
(desde C++11)
  • Si ! uppercase , utilizará el especificador de conversión % g .
  • En caso contrario, utilizará el especificador de conversión % G .
Además:
  • Si el tipo de val es long double , se añade el modificador de longitud L al especificador de conversión.
  • Si el tipo de val es un tipo de punto flotante y floatfield ! = ( ios_base :: fixed | ios_base :: scientific ) (desde C++11) , se añade el modificador de precisión y se establece en str. precision ( ) . En caso contrario, no se especifica precisión.
  • Para tipos enteros y de punto flotante, si showpos está activado, el modificador + se antepone.
  • Para tipos enteros, si showbase está activado, el modificador # se antepone.
  • Para tipos de punto flotante, si showpoint está activado, el modificador # se antepone.
  • Si el tipo de val es void * , se utilizará el especificador de conversión % p
  • Una cadena de caracteres estrechos se crea como si mediante una llamada a std:: printf ( spec, val ) en la configuración regional "C", donde spec es el especificador de conversión elegido.

Etapa 2: conversión específica de la configuración regional

Etapa 3: padding

  • La bandera de ajuste se obtiene como si fuera mediante std :: fmtflags adjustfield = ( flags & ( std:: ios_base :: adjustfield ) ) y se examina para identificar la ubicación del relleno, como sigue:
  • Si str. width ( ) es distinto de cero (por ejemplo, se acaba de usar std::setw ) y el número de CharT después de la Etapa 2 es menor que str. width ( ) , entonces se insertan copias del carácter de relleno fill en la posición indicada por el relleno para llevar la longitud de la secuencia a str. width ( ) .

En cualquier caso, str. width ( 0 ) se llama para cancelar los efectos de std::setw .

Etapa 4: salida

Cada carácter sucesivo c de la secuencia de CharT 's de la Etapa 3 se emite como si fuera mediante * out ++ = c .

Parámetros

out - iterador que apunta al primer carácter que será sobrescrito
str - flujo del cual obtener la información de formato
fill - carácter de relleno utilizado cuando los resultados necesitan ser ajustados al ancho del campo
val - valor a convertir a cadena y mostrar

Valor de retorno

out

Notas

El cero inicial generado por la especificación de conversión #o (resultante de la combinación de std::showbase y std::oct por ejemplo) no se cuenta como un carácter de relleno.

Al formatear un valor de punto flotante como hexfloat (es decir, cuando floatfield == ( std:: ios_base :: fixed | std:: ios_base :: scientific ) ), la precisión del flujo no se utiliza; en su lugar, el número siempre se imprime con suficiente precisión para representar exactamente el valor.

(since C++11)

Ejemplo

Mostrar un número usando el facet directamente, y demostrar un facet definido por el usuario:

#include <iostream>
#include <locale>
// this custom num_put outputs squares of all integers (except long long)
struct squaring_num_put : std::num_put<char>
{
    iter_type do_put(iter_type out, std::ios_base& str,
                     char_type fill, long val) const
    {
        return std::num_put<char>::do_put(out, str, fill, val * val);
    }
    iter_type do_put(iter_type out, std::ios_base& str,
                     char_type fill, unsigned long val) const
    {
        return std::num_put<char>::do_put(out, str, fill, val * val);
    }
};
int main()
{
    auto& facet = std::use_facet<std::num_put<char>>(std::locale());
    facet.put(std::cout, std::cout, '0', 2.71);
    std::cout << '\n';
    std::cout.imbue(std::locale(std::cout.getloc(), new squaring_num_put));
    std::cout << 6 << ' ' << -12 << '\n';
}

Salida:

2.71
36 144

Una implementación de operator<< para un tipo definido por el usuario.

#include <iostream>
#include <iterator>
#include <locale>
struct base { long x = 10; };
template<class CharT, class Traits>
std::basic_ostream<CharT, Traits>&
    operator<<(std::basic_ostream<CharT, Traits>& os, const base& b)
{
    try
    {
        typename std::basic_ostream<CharT, Traits>::sentry s(os);
        if (s)
        {
            std::ostreambuf_iterator<CharT, Traits> it(os);
            std::use_facet<std::num_put<CharT>>(os.getloc())
                .put(it, os, os.fill(), b.x);
        }
    }
    catch (...)
    {
        // set badbit on os and rethrow if required
    }
    return os;
}
int main()
{
    base b;
    std::cout << b;
}

Salida:

10

Informes de defectos

Los siguientes informes de defectos que modifican el comportamiento se aplicaron retroactivamente a los estándares de C++ publicados anteriormente.

DR Se aplica a Comportamiento publicado Comportamiento correcto
LWG 34 C++98 la sobrecarga de bool utilizaba miembros inexistentes
truename y falsename de std::ctype
utiliza estos miembros
de std::numpunct
LWG 231 C++98 el modificador de precisión solo se añadía si
( flags & fixed ) ! = 0 o str. precision ( ) > 0
eliminó estas condiciones
LWG 282 C++98 los separadores de miles solo se
insertaban para tipos integrales en la etapa 2
también se insertan para
tipos de punto flotante
LWG 4084 C++11 "NAN" y "INF" no se podían imprimir se pueden imprimir

Véase también

inserta datos formateados
(función miembro pública de std::basic_ostream<CharT,Traits> )