Konwersja float na const char*

0

W jaki sposób mogę przekonwertować zmienną float na const char* ?
Zrobiłem coś takiego:

float var = 12.34
(std::to_string(var)).c_str()

i to nawet działa, tylko że w wyniku tej operacji dostaję 21.3400000, a potrzebuję tylko dwie cyfry po przecinku.

1

Możesz spróbować przez stringstream:

ostringstream ss;
ss << setprecision(3) << f;
const char* str = ss.str().c_str();

Jakoś tak, napisałem z palca, musisz sprawdzić czy działa.

0

Powyższa metoda niestety nie wyświetla mi żadnego napisu. Spróbowałem jeszcze zrobić tak:

	const char* val = (std::to_string(data.dx.vol)).c_str();
	char valC[6];

	for (int i = 0; i < 5; i++) {
		valC[0] = *(val + i);
	}

i valC przekazać do funkcji ale niestety też nie działa. Natomiast jeżeli napiszę valC[6] = "12.34" i to przekażę jako parametr do funkcji to się wyświetla. Musi więc być to wina konwersji i prawdopodobnie jak twonek wyżej wspomniał pewnie coś z tym wskaźnikiem jest nie tak.

1
valC[0] = *(val + i);

skoro do tej samej komórki valC[0] zapisujesz kolejne literki, to jak ma działać?

Ale ta metoda jest ułomna z definicji. c_str() się używa od razu w wywołaniu funkcji, bo tylko wtedy masz gwarancję poprawności danych.

3

@mlp jeżeli dobrze zrozumiałem, że stringa potrzebujesz przekazać do jakiejś funkcji, i chcesz tylko pierwsze pięć znakó

void yourFunc(const char *strFloat) { ... }

const auto str  = std::to_string(data.dx.vol).substr(0,5);

yourFunc(str.c_str());
1

Miks pierwszej i ostatniej wersji:

#include <iostream>
#include <sstream>
#include <iomanip>

using namespace std;

void myFunc(const char *strFloat) {
	cout << "myFunc: ";
	while(*strFloat) {
		cout << *(strFloat++);
	}
	cout << endl;
}

int main() {
  const float var = 12.34;	
  ostringstream ss;
  ss << std::fixed << setprecision(2) << var;
  myFunc(ss.str().c_str());
  return 0;
}

http://ideone.com/ocOgkL

6

Ale kombinujecie.

char buf[32];
sprintf(buf, "%.2f", 12.34);

ewentualnie

std::stringstream foo;
foo << std::fixed << std::setprecision(2) << 12.34;
std::string out;
foo >> out;

Jak dla mnie metoda z format stringiem jest tutaj czytelniejsza, strzelałbym też, że szybsza.

A sposób zaprezentowany w innych miejscach, t.j. wywoływanie .c_str() na obiekcie tymczasowym jest szalenie zdradliwy. Czas życia danych wskazywanych przez ten wskaźnik jest równy czasowi życia obiektu tymczasowego, więc nawet jeśli @several i @vpiotr zastosowali go poprawnie, to bardzo bym odradzał jego stosowanie w praktyce. Szczególnie przez mniej doświadczonych programistów.

0
mlp99 napisał(a):

W jaki sposób mogę przekonwertować zmienną float na const char* ?
Zrobiłem coś takiego:

float var = 12.34
(std::to_string(var)).c_str()

i to nawet działa, tylko że w wyniku tej operacji dostaję 21.3400000, a potrzebuję tylko dwie cyfry po przecinku.

liczba zmiennoprzecinkowa nie ma takiej czy innej ilości cyfr po przecinku. Jest po prostu liczbą, w rzeczywistości binarną. Wypadało by odróżniać liczbę od jej widzialnego formatowania na 'outpucie'.

Co więcej, niektóre liczby nie istnieją (problem reprezentacji).
Przykładowa** float 12.34** też** nie istnieje**. jej "bardziej prawdziwa" wartość to 12.3400002 (może jakaś inna platforma wyliczy przykładowo 12.339997).

Niestety wiedza o zmiennym przecinku kiedyś tak podstawowa, jakoś zanikła wśród mas programistycznych. To czasem może skopać pewną część ciała. Jeszcze o ograniczonej dokładności ktoś by sobie coś przypomniał, o problemie reprezentacji nieliczni. Zarówno biblioteki, a zwłaszcza IDE robią MSZ krzywdę jak prezentują liczby zbyt "przyjaźnie" (a fałszywe)

Użyta w innym miejscu liczba to 21.3400002.

Zgadzam się z kolegami, którzy przestrzegają przed c_str() itd, te fragmenty są pełne UB/ błedów... ale mi to dodatkowo pachnie jakimś problemem XY

1 użytkowników online, w tym zalogowanych: 0, gości: 1