2009-09-30 8 views
1

Je souhaite convertir un double en chaîne de largeur fixe.Convertir le double en chaîne avec une largeur fixe

Si la largeur est 10, alors je veux que la valeur double soit arrondie à cette largeur.

Par exemple, si la valeur = 102,121323435345 et la largeur est de 10, cette valeur devrait être,

 
position==> 
      value = 102.121323 

je peux y parvenir avec snprintf, mais je suis à la recherche d'un C++ code natif pour faire la même chose.


char buf[125]; 
snprint(buf, width, "%.6f", value); 

J'ai essayé d'utiliser le ci-dessous, mais il ne me aide pas beaucoup,


std::ostringstream oss; 
oss << std::fixed << std::setw(10) << std::precision(6) << value; 

std :: guarantiees setw la largeur minimale de la valeur et si la valeur est supérieure à la taille de la largeur , ça ne termine pas les valeurs.

Merci.

+0

Quelque chose qui n'est pas tout à fait clair pour moi: essayez-vous d'imprimer avec une largeur de 10 comme dans votre exemple de sortie, ou 4 décimales, comme dans votre code c? – Martin

+0

Pourquoi êtes-vous contre l'utilisation de snprintf? C'est parfaitement valide C++. L'ostringstream est exagéré pour cela. – Vitali

+0

@Martin, je veux que la largeur soit constante –

Répondre

1

Est-ce ce que vous voulez? Ici, nous calculons la quantité de précision disponible et réglons l'ostream en conséquence.

#include <iostream> 
    #include <iomanip> 

    using namespace std; 

    int main(int argc, char* argv[]) 
    { 
    // Input 
    double value = 102.1213239999; 
    // Calculate limits 
    int digits = ((value<1) ? 1 : int(1+log10(double(abs(value))))); 
    int width = 10; 
    int precision = (((width-digits-1)>=0) ? (width-digits-1):0); 

    // Display 
    cout.setf(ios::fixed); 
    cout.precision(precision); 
    cout<<setw(10)<<value<<endl; 


    return 0; 

    } 
    OUTPUT: 102.121324 

BTW, si vous voulez un camion plein de façons de calculer chiffres, here's how.

+0

OP veut une sortie maximale de 10 caractères avec une précision maximale. – mob

+0

Que se passe-t-il lorsque la valeur> 1e9? – Jacob

+0

Que diriez-vous de maintenant? Il ne restera pas à 10 caractères s'il est supérieur à 1e9 mais le problème de précision est résolu (je pense). – Jacob

2

Qu'en est-cast lexical?

double x = 102.1213239999; 
std::cout << boost::lexical_cast<std::string>(x).substr(0,10); 

Ce n'est pas exactement ce que vous avez demandé. J'essayais juste de sortir des sentiers battus.
Vous pouvez également examiner cette question pour une discussion sur le formatage differences between C and C++ et consultez la Boost Format Library

+1

C'est faux. Considérez ce numéro: double x = 12345678901. Votre réponse va être erronée par ordre de grandeur. – Vitali

+0

Même si l'exemple est faux, la suggestion de regarder la bibliothèque Boost Format vaut +1. – MP24

+0

@unknown: Je trouve que les déclarations absolues sont généralement fausses (ce n'est probablement pas une bonne solution).Je sais que les grandes valeurs seront tronquées, mais la question est d'adapter les données dans un champ de sortie de taille fixe, pas de précision (sinon la solution est triviale, utilisez la largeur du manipulateur (10)). Dans la question d'origine snprint() est utilisée pour tronquer la sortie, cette alternative fournit une solution équivalente (mais plus simple) en C++. La vraie question est de savoir ce que vous faites quand vous avez un champ de sortie de taille fixe et que la valeur est plus grande! C'est pourquoi width (x) spécifie une largeur minimale et non une largeur maximale. –

2

Vous pouvez utiliser la fonction osteram::width et ostream::precision pour atteindre votre objectif, comme celui-ci

std::ostringstream out; 
out.width(10); 
out.precision(10); 
out << 123.12345678910111213; 

Bien qu'il a gagné N'ajoutez pas de zéros après le point afin de respecter la largeur mais il ajoutera des espaces (ou n'importe quel caractère de votre choix) avant le nombre. Donc, vous obtiendrez '102' ou '0000000102' (si vous appelez out.fill ('0');) au lieu de '102.000000' si vous passez 102 comme valeur d'entrée.

Questions connexes