Как из float сделать string c
Нравится ресурс?
Правила раздела Visual C++ / MFC / WTL (далее Раздела)
1) На Раздел распространяются все Правила Форума.
2) Перед тем, как создать новый топик, убедитесь, что Вы читали Правила создания тем в Разделе.
3) Вопросы, не связанные с программированием (настройки MS Visual Studio, книги, библиотеки и т.д.),
обсуждаются в разделе C/C++: Прочее
4) Вопросы разработки .NET (Windows Form, C++/CLI и т.п.) приложений на Visual C++/C# обсуждаются в разделе .NET.
5) Нарушение Правил может повлечь наказание со стороны модераторов.
Как конвертировать float/double в строку именно в том виде, в котором значение устновленно в переменной (без обрезки занков)?
Выводит «0.01234567», а надо «0.012345678900000». stringstream пробовал — результат тот же. std::to_string вообще 6 знаков пишет после точки. Точность заранее не известна, нужно выгружать в строку то, что есть, можно без нулей в конце. Как это сделать?
Отслеживать
задан 8 мая 2020 в 18:27
2,273 1 1 золотой знак 17 17 серебряных знаков 27 27 бронзовых знаков
А вы не задумывались, какова точность представления числа типом float ?
8 мая 2020 в 18:29
@Harry с double картина не меняется
8 мая 2020 в 18:31
Ну, вы вообще бредом занимаетесь — в пустой string что-то писать.
8 мая 2020 в 18:35
Ну, конкретное количество нулей справа — это вы никак не получите. У гугла есть библиотека, которая печататет числа с плавающей точкой за минимальное количество знаков, возможно это вам подойдет. (По идее, std::to_chars тоже должна так уметь, но пока ее завезли только в MSVC.)
8 мая 2020 в 18:58
1 ответ 1
Сортировка: Сброс на вариант по умолчанию
float valf = 0.012345678900100; double vald = 0.012345678900100; printf("%.20f\n", valf); printf("%.20lf\n", vald);
0.01234567910432815552 0.01234567890010000030
В любом случае в силу того, что числа с плавающей точкой представлены в итоге виде суммы степеней двойки, ожидать, что введенный строковый литерал или результат вычисления будет равен чему-то конкретному, не приходится.
char buf[30]; sprintf(buf,"%.20lf",val); string s = buf;
ostringstream os; os
Только не пишите в никуда, как в вашем примере.
Update
К "артефактам", упомянутым в комментарии. Это не артефакты. Представим, что у нас есть возможность записи только 4 бит. Как вы представите, например, 1/5 в виде суммы дробей вида 1/2 n ?
1/8 + 1/16 + 1/128. Стоп! Уже не можем представить 1/128 - точности не хватает. Так что число 0.20 будет иметь вид 0.1875.
Это - ограничение самого представления. Ну невозможно в общем случае представить дробное число с помощью конечной суммы дробей вида 1/2 n .
Как из float сделать string c
AD>ЗЫ: правда получишь жуткие тормоза.
из-за чего?
(я хочу это использовать для генерации sql запросов)
Re[3]: Как правильно преобразовать float в string
| От: | ArtDenis | |
| Дата: | 01.05.03 13:43 | |
| Оценка: | 2 (1) | |
Здравствуйте, AI, Вы писали:
AD>>ЗЫ: правда получишь жуткие тормоза.
AI>из-за чего?
#include #include const count = 10000; void test1() < std::string str; std::ostringstream tmp; int i; float value = 11.765765; for (i = 0; i < count; i++) < tmp.clear(); tmp > void test2() < std::string str; char buffer[64]; int i; float value = 11.765765; for (i = 0; i < count; i++) < sprintf(buffer, "%f", value); str = buffer; > >
Так вот test1 у меня отрабатывает за 2.7 секунд, test2 — за 0.025. Комментарии, я думаю, излишни.
AI>(я хочу это использовать для генерации sql запросов)
Для этого — в самый раз. Тем более, что ostringstream может растягиваться до любых (почти) размеров.
Re[4]: Как правильно преобразовать float в string
| От: | КАА |
| Дата: | 01.05.03 15:06 |
| Оценка: |
Как насчет _gcvt() .
Все будет Украина!
Re: Как правильно преобразовать float в string
| От: | WFrag | |
| Дата: | 01.05.03 15:09 | |
| Оценка: | 21 (2) | |
Здравствуйте, AI, Вы писали:
AI>я делаю так
AI>char cstring[10];
AI>float a=80.01;
AI>sprintf(cstring,"%f",a);
AI>std::string str=""+cstring+"";
AI>--------------------------------
AI>как правильно сделать
AI>а вот ещё так бы хотелось
AI>vector v(10);
AI>--------------------------------
А еще можно c помощью boost:
string str = lexical_cast( 1.2345f );
Re[5]: Как правильно преобразовать float в string
| От: | ArtDenis |
| Дата: | 01.05.03 15:24 |
| Оценка: |
Здравствуйте, КАА, Вы писали:
КАА>Как насчет _gcvt() .
А так же fcvt, ecvt. Каждый вибирает для себя наиболее удобный вариант. Все сишные реализации небезопасны с точки зрения вероятности записи за пределы буфера, зато они очень быстро работают. С ostringstream всё наоборот — он безопасен и многофункционален, но работает медленно.
Re[4]: Как правильно преобразовать float в string
| От: | Михаил Можаев | www.mozhay.chat.ru |
| Дата: | 01.05.03 23:48 | |
| Оценка: | 6 (1) | |
Здравствуйте, ArtDenis, Вы писали:
AD>>>ЗЫ: правда получишь жуткие тормоза.
AD>Так вот test1 у меня отрабатывает за 2.7 секунд, test2 — за 0.025. Комментарии, я думаю, излишни.
А зачем так хитро? Попробуй так:
void test1() < std::string str; int i; float value = 11.765765; for (i = 0; i < count; i++) < std::ostringstream tmp; tmp >
И все уже не так плохо
Re[5]: Как правильно преобразовать float в string
| От: | ArtDenis |
| Дата: | 02.05.03 05:59 |
| Оценка: |
Здравствуйте, Михаил Можаев, Вы писали:
ММ>
ММ>void test1() ММ> < ММ>std::string str; ММ> int i; ММ> float value = 11.765765; ММ> for (i = 0; i < count; i++) ММ> < ММ>std::ostringstream tmp; ММ> tmp str = tmp.str(); ММ> > ММ>> ММ>
ММ>И все уже не так плохо
В полтора раза быстрее
Re[2]: Как правильно преобразовать float в string
| От: | ArtDenis |
| Дата: | 02.05.03 07:26 |
| Оценка: |
Здравствуйте, WFrag, Вы писали:
WF>А еще можно c помощью boost:
WF>
WF>string str = lexical_cast( 1.2345f ); WF>
2.3 секунды с lexical_cast против секунд 0.025 с sprintf
Re[3]: Как правильно преобразовать float в string
| От: | WFrag |
| Дата: | 02.05.03 11:34 |
| Оценка: |
Здравствуйте, ArtDenis, Вы писали:
AD>Здравствуйте, WFrag, Вы писали:
WF>>А еще можно c помощью boost:
WF>>
WF>>string str = lexical_cast( 1.2345f ); WF>>
AD>2.3 секунды с lexical_cast против секунд 0.025 с sprintf
AD>Денис.
Ну lexical_cast<> собственно вот по такому принципу и работает :
float a = 80.01; std::string str; std::stringstream tmp; tmp
Re[4]: Как правильно преобразовать float в string
| От: | AI |
| Дата: | 02.05.03 13:56 |
| Оценка: |
Cпасибо всем . я остановился на потоке ostringstream /
но у меня почему не дейтсует
tmp.clear();
то есть просиходит процесс добавления. пришлось каждый раз создавать новый
Re[5]: Как правильно преобразовать float в string
| От: | Павел Кузнецов | |
| Дата: | 02.05.03 14:26 | |
| Оценка: | 12 (1) | |
Здравствуйте, AI, Вы писали:
A> остановился на потоке ostringstream /
A> но у меня почему не дейтсует tmp.clear();
tmp.clear() вместо ожидаемой тобой "очистки содержимого" просто-напросто сбрасывает флаг состояния. Используй
tmp.str(std::string());
float to string на эмбедах, без sprintf, как?
Посоветуйте, чем можно обычный float перегнать в строку, с заданной точностью? А то по всяким stackoverflow какие-то васянские снипеты и мутные самоделки с непонятными лицензиями. Сейчас юзаю sprintf, но он помимо жирности кастует float в double, что вызывает дополнтельное распухание зависимостей.
Мне не надо наворотов sprintf, хватило бы просто «распечатать с XX знаками после запятой», можно даже без отрицательных значений. Может есть какие-то известные библиотеки, от которых эмбед не треснет?
PS. Закопипастить 30 строк кода всегда успеется. Сначала хочу попробовать найти и заюзать библиотеку.

Vit ★★★★★
03.10.19 11:37:07 MSK
Сначала хочу попробовать найти и заюзать библиотеку.
Что там юзать? Сперва отсекаешь целое, потом берешь остаток, записываешь его в char* и делишь это целое в цикле на 10, пока не кончится. Дробную часть умножаешь на 10, пока не надоест, записывая целое в char*.
crutch_master ★★★★★
( 03.10.19 11:55:50 MSK )
Последнее исправление: crutch_master 03.10.19 11:56:51 MSK (всего исправлений: 1)

Заюзай xprintf же!
shkolnick-kun ★★★★★
( 03.10.19 12:37:45 MSK )
Ответ на: комментарий от shkolnick-kun 03.10.19 12:37:45 MSK
crutch_master ★★★★★
( 03.10.19 12:41:37 MSK )
Ответ на: комментарий от crutch_master 03.10.19 11:55:50 MSK

Мне в эмбедах не нравится, что каждый городит помойку собственных лисапедов. Скопипастить код не проблема, но хочется «красиво» - подключить зависимость в platformio или заюзать что-то готовое из стандартного.
Vit ★★★★★
( 03.10.19 13:01:37 MSK ) автор топика
Ответ на: комментарий от crutch_master 03.10.19 12:41:37 MSK

Это лишний раз доказывает, что флоат в имбеде нинужно!
shkolnick-kun ★★★★★
( 03.10.19 13:01:49 MSK )
Ответ на: комментарий от Vit 03.10.19 13:01:37 MSK

У тебя неправильные представления об этом всем.
Быстрее велосипед написать, чем заниматься поиском всякого нинужно на гитхабах
shkolnick-kun ★★★★★
( 03.10.19 13:02:36 MSK )
Последнее исправление: shkolnick-kun 03.10.19 13:03:29 MSK (всего исправлений: 1)
anonymous
( 03.10.19 13:08:14 MSK )
Ответ на: комментарий от anonymous 03.10.19 13:08:14 MSK

О, в ETL что-то есть на эту тему.
Vit ★★★★★
( 03.10.19 13:23:13 MSK ) автор топика
Ответ на: комментарий от crutch_master 03.10.19 11:55:50 MSK
Что там юзать? Сперва отсекаешь целое, потом берешь остаток, записываешь его в char* и делишь это целое в цикле на 10, пока не кончится. Дробную часть умножаешь на 10, пока не надоест, записывая целое в char*.
после взятия целого и остатка всё прочее лишнее. выводишь их как 16-тиричные, что почти моментально.. и получаешь результат аналогичный printf(«%a»,x) ..
может непривычно, но на то и эмбед. Зато кстати точность не теряется
MKuznetsov ★★★★★
( 03.10.19 17:02:08 MSK )
Ответ на: комментарий от MKuznetsov 03.10.19 17:02:08 MSK

Если ему так нужны флоаты, то, почему не сделать:
а) отдельно хранимые целое и дробное (как целое) и нужные функции по умножению, делению, сложению, вычитанию, выводу
б) условится, что целое меньше N разрядов (до нужной точности) — это дробная часть
deep-purple ★★★★★
( 03.10.19 17:15:57 MSK )
не то чтобы у меня дикий опыт в эмбедах, но он весь говорит что float на эмбедах это ошибка архитектуры. Замени float и уйдёт эта и куча другого не нужного хлама.
vtVitus ★★★★★
( 03.10.19 17:55:00 MSK )
Ответ на: комментарий от vtVitus 03.10.19 17:55:00 MSK

Ага, заодно еще посоветуй интерфейс превратить в кусок говна, как это принято на эмбедах. Потому что красивый интерфейс - это нарушение традиций.
Vit ★★★★★
( 03.10.19 18:15:25 MSK ) автор топика
Ответ на: комментарий от Vit 03.10.19 18:15:25 MSK
но ведь дело говорит. эмбеды обычно начинаются с определения числа значящих цифр, дальше сам догадаешся? хотя я выше уже питонячью обстракцию тебе кинул на подумать, видимо ты опять уперся
хм, не ну если ты только не калькулятор там пилишь (:
Morin ★★★★
( 03.10.19 18:47:58 MSK )
Последнее исправление: Morin 03.10.19 18:49:16 MSK (всего исправлений: 1)
Ответ на: комментарий от Morin 03.10.19 18:47:58 MSK

Нету там ни какого дела. Мог бы проект открыть, и посмотреть что там где я использую плавучку, кроилово нафик не уперлось. В интерфейсе важнее чтобы клепать быстро и менять легко.
А великие экономисты обычно лепят говнарские интерфейсы и просто не в состоянии представить, что иногда надо решать задачи поважнее экономии битов и тактов.
Vit ★★★★★
( 03.10.19 19:42:43 MSK ) автор топика
Ответ на: комментарий от Vit 03.10.19 19:42:43 MSK
ты сам наверху страдал по даблу, ну нельзя быть таким непоследовательным (: теперь оказывается ресурсы неважны
Morin ★★★★
( 03.10.19 20:04:45 MSK )
Есть, бери.
Могу посоветовать свой вариант d2a() , с тестом корректности и отдельным benchmark-ом.
По текущей информации это самая быстрая, компактная и корректная реализация d2a по мотивам алгоритма grisu. Ryu (пока) обгоняет её только потому, что я всегда генерирую полную строку (мне так надо было).
В бенчмарке собраны примерно все релевантные реализации d2a, поэтому можно посмотреть на альтернативы.
Функция d2a() преобразует double в корректную строку минимальной длины вида -22250738585072014e-324 , так чтобы обратное преобразование в double всегда дает исходное значение (но при этом, последняя цифра может быть +/-1 от оптимально близкой). Эту строку дальше можно легко превратить в желаемый формат.
Минусы: только double, код на C++, «сырой» формат результата (ничего лишнего, даже без \0 на конце).
Deleted
( 03.10.19 20:11:12 MSK )
Ответ на: комментарий от Morin 03.10.19 20:04:45 MSK

Не важны. Но мне не нравятся варнинги компилятора и есть желание поразбираться, как на сях лепить эмбеды дешево и сердито.
В общем я все динамические строки на ETL перевел. Годная штука.
Vit ★★★★★
( 03.10.19 20:12:17 MSK ) автор топика
Ответ на: Есть, бери. от Deleted 03.10.19 20:11:12 MSK

Спасибо. Я пока это заюзал https://www.etlcpp.com/to_string.html. Заодно будет повод в sdl поразбираться, сто лет уже на сях и плюсах не кодил.
Vit ★★★★★
( 03.10.19 20:26:51 MSK ) автор топика
Ответ на: комментарий от Vit 03.10.19 18:15:25 MSK
Ага, заодно еще посоветуй интерфейс превратить в кусок говна
«чую теоретика развитого социализма». ты бы с первых строк сказал, что твоё поделие «сферическое в вакууме», а то тебе помочь пытались исходя из опыта, а нужно исходить из красивых и не имеющих отношения к реальности картинок.
vtVitus ★★★★★
( 04.10.19 07:29:29 MSK )
Ответ на: комментарий от vtVitus 04.10.19 07:29:29 MSK

Зачем мне про себя что-то придумывать? Ссылку уже сто раз давал, видимо кроме тебя в танке больше никого не осталось. И таки да, совершенно не обязательно «пытаться мне помогать» по тем вопросам, где я совета не спрашивал.
Vit ★★★★★
( 04.10.19 07:37:09 MSK ) автор топика
Ответ на: комментарий от Vit 03.10.19 20:12:17 MSK
мда, походу в модеиаторы набрали полотеров, снесли все до кучи (:
Morin ★★★★
( 04.10.19 09:44:58 MSK )
Ответ на: комментарий от Morin 04.10.19 09:44:58 MSK
мда, походу в модераторы набрали полотеров, снесли все до кучи (:
Полотеры с синдромом вахтера? Горючая смесь!
anonymous
( 04.10.19 09:48:33 MSK )
Ответ на: комментарий от Morin 04.10.19 09:44:58 MSK

Без советов Эдика я переживу. Причем даже лучше чем с ними. Жалко что он сам это не хочет понимать.
Vit ★★★★★
( 04.10.19 11:01:15 MSK ) автор топика
Ответ на: комментарий от Vit 04.10.19 11:01:15 MSK
Он безвредный алкач, иногда буянит, но с него бывает толк
За последние несколько лет, что-то узнал с лора, всего от пары человек, персонаж один из них.
Увы лор много лет как, лор не является местом для решения проблем ни новичков, ни старожилов мира линукс
anonymous
( 04.10.19 11:06:13 MSK )
Ответ на: комментарий от anonymous 04.10.19 11:06:13 MSK
За последние несколько лет, что-то узнал с лора, всего от пары человек, персонаж один из них.
anonymous
( 04.10.19 11:08:53 MSK )
Ответ на: комментарий от Morin 04.10.19 09:44:58 MSK

фотачки второй версии платы воображаемого диспенсера 🙂
дисплейчик удачно воткнулся по размерам.