Obsługa jednocześnie przecinka lub kropki w konwersji na float [Borland C++]

0

Jak w temacie.
Chcę, aby użytkownik nie musiał się martwić czym rozdziela liczby całkowite od dziesiętnych. Zrobiłem to w ten sposób:

 float TForm1::spr_float(AnsiString str)
{
float ret;
        if ( str=="" ) ret = 0;	// jeśli puste pole, zwraca 0 //
        else if ( StrToFloatDef(str, 0) ) ret = StrToFloat(str) ;	// jeśli przecinek, konwertuje //
        else ret = atof(str.c_str());	// jeśli kropka //
return ret;
}

I wszystko ładnie działa, jednak jest duże ALE: Tylko u mnie na komputerze. Jak przeniosę program na inną maszynę, to raz obsługuje kropki/przecinki, ale w większości same kropki.

I to jest ból, bo w niektóre pola wczytuję dane skanerem, a tam separatorem jest "." (kropka), ale często w te same pola wpisuje się dużo danych ręcznie używając bloku numerycznego, a tam separatorem jest "," przecinek.
Wiem, że można w systemie zrobić, żeby była tam kropka zamiast przecinka, ale to odpada - musi tam być przecinek.

Proszę o pomoc.

0

Przeleć znak po znaku i po prostu zamień napotkany przecinek na kropkę, skoro i tak do stringa wczytujesz.

char *f = new char [str.size()+1];
strcpy (f, str.c_str());
for(int i=0; f[i]>0; i++){
  if(f[i]==','){
    f[i]='.';
    break;
  }
  if(f[i]=='.') break;
}
return atof(f);

nagłówek cstring (chyba że to jakaś wersja borlanda z epoki dinozaurów, wtedy string.h, ale chyba nie skoro jest AnsiString). Chyba jest niejawnie includowany.
//EDIT: poprawka literówki w 2 linijce kodu

0

A Próbowałeś Tak:
char *f = new char [str.size(1)+1];
strcpy (f, str,c_str()
for(int i=0; f[i]>0; i++){
if(f[i]==','){
f[i]='.';
break;
)
if(f[0]=='.') break;
)
return atof(g);
Jak Tak To Spróbuj Kod Catch

0

Ok, dzięki za pomoc, już działa dobrze Waszym sposobem :)
jedyne co zmieniłem, to

 char *f = new char [str.size(1) + 1];

na operator sizeof():

 char *f = new char [sizeof(str) + 1];
0

nie byłbym tego taki pewien... Wiesz co robi sizeof? Zwraca wielkość obiektu. A w AnsiString (różni się czymś od std::string?) jest wskaźnik do tablicy znaków. Wskaźnik nawet do 1000 znaków zajmuje 4, lub 8 bajtów. Długość char[]a sprawdza się funkcją strlen, a stringa metodą .size(), ew strlen(str.c_str());

Zatem jeżeli str jest typem AnsiString (posłużę się przykładem std::string, bo borlanda nie mam), to jego sizeof zwraca 4, czyli tworzy ci tablicę 5 znaków (w tym jeden na \0)

  std::string str="Przykładowy ciąg znaków";
  printf("%d\n", sizeof(str)); //Wypisze "4" na 32-bitowym systemie
  printf("%d\n", str.size()); //Wypisze 26, bo polskie znaki liczą się jako 2 w UTF-8, a nie liczy \0 na końcu

Może dla prostych przykładów działa, ale pewnego dnia może ci wyskoczyć "Segmentation fault", bo za mało miejsca przydziela.

0
double x = StringReplace(editor-text, DecimalSeparator=='.'?",":".", DecimalSeparator, TReplaceFlags() << rfReplaceAll).ToDouble();

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