Подтвердить что ты не робот

Преобразовать число с плавающей точкой в строку с указанием точности и количества десятичных цифр?

Как вы конвертируете float в строку на С++, указав точность и количество десятичных цифр?

Например: 3.14159265359 -> "3.14"

4b9b3361

Ответ 1

Типичным способом было бы использовать stringstream:

#include <iomanip>
#include <sstream>

double pi = 3.14159265359;
std::stringstream stream;
stream << std::fixed << std::setprecision(2) << pi;
std::string s = stream.str();

Смотрите исправлено

Используйте фиксированную запись с плавающей точкой

Устанавливает floatfield флаг формата для потока, чтобы ул fixed.

Если для floatfield с плавающей запятой задано fixed, значения с плавающей запятой записываются с использованием записи с фиксированной запятой: значение представляется с точно таким количеством цифр в десятичной части, которое указано в поле precision (precision), и без экспоненты.

и установить точность.


Для преобразований технического назначения, таких как хранение данных в файле XML или JSON, С++ 17 определяет семейство функций to_chars.

Предполагая совместимый компилятор (которого у нас нет на момент написания), можно рассмотреть что-то вроде этого:

#include <array>
#include <charconv>

double pi = 3.14159265359;
std::array<char, 128> buffer;
auto [ptr, ec] = std::to_chars(buffer.data(), buffer.data() + buffer.size(), pi,
                               std::chars_format::fixed, 2);
if (ec == std::errc{}) {
    std::string s(buffer.data(), ptr);
    // ....
}
else {
    // error handling
}

Ответ 2

Обычным методом для выполнения такого рода является "print to string". В С++ это означает использование std::stringstream что-то вроде:

std::stringstream ss;
ss << std::fixed << std::setprecision(2) << number;
std::string mystring = ss.str();

Ответ 3

Другой вариант snprintf:

double pi = 3.1415926;

std::string s(16, '\0');
auto written = std::snprintf(&s[0], s.size(), "%.2f", pi);
s.resize(written);

Демо. Должна быть добавлена ​​обработка ошибок, т.е. Проверка на written < 0.

Ответ 4

Вы можете использовать функцию fmt::format из библиотеки {fmt}:

#include <fmt/core.h>

int main()
  std::string s = fmt::format("{:.2f}", 3.14159265359); // s == "3.14"
}

где 2 - точность.

Это средство форматирования было предложено для стандартизации в C++: P0645. И P0645, и {fmt} используют синтаксис строки формата, подобный Python, который аналогичен printf но вместо % использует {} качестве разделителей.

Ответ 5

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

float num=99.463;
float tmp1=round(num*1000);
float tmp2=tmp1/1000;
cout << tmp1 << " " << tmp2 << " " << to_string(tmp2) << endl;

Вы получаете

99463 99.463 99.462997

Примечание: переменная num может быть любым значением, близким к 99.463, вы получите тот же распечаток. Дело в том, чтобы избежать удобной функции С++ 11 "to_string". Мне потребовалось некоторое время, чтобы выбраться из этой ловушки. Лучший способ - методы stringstream и sprintf (язык C). С++ 11 или newer должен предоставить второй параметр в виде числа цифр после показания плавающей запятой. Сейчас по умолчанию - 6. Я полагаю, что другие не будут тратить время на эту тему.

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

string ftos(float f, int nd) {
   ostringstream ostr;
   int tens = stoi("1" + string(nd, '0'));
   ostr << round(f*tens)/tens;
   return ostr.str();
}