Форум программистов, компьютерный форум CyberForum.ru
Наши страницы

С++ для начинающих

Войти
Регистрация
Восстановить пароль
 
Рейтинг: Рейтинг темы: голосов - 11, средняя оценка - 4.64
Sylvos
-25 / 6 / 1
Регистрация: 06.04.2011
Сообщений: 85
#1

Str в long double и наоборот - C++

19.09.2011, 16:14. Просмотров 1417. Ответов 9
Метки нет (Все метки)

Одним из недостатков C++ являеться отсутствие для бизнес-программ встроенного типа для денежных значений, такого, как $173 698 001,32. Такой денежный тип должен иметь возможность для хранения числа с фиксированноой десятичной точкой точностью около 17 знаков, которого было бы достаточно для хранения национального долга в долларах и центах.К счастью, встроенный тип С++ long bouble имеет точность 19 цифр, плэтому мы можем использовать его как базисный для класса money, даже импользуя плавающую точку. Однако нам нужно будет добавить возможность ввода и вывода денежных значений с предшествующим им знаком доллара и разделенными запятыми группы по три числа: так проще читать большие числа. Первым делом при разработке такого класса напишем метод mstold(), который принимает денежную строку, то есть строку, представляющую собой некоторое количество денег типа "$1,234,567,890,123.99" вкачестве аргумента и возвращает эквивалентное ее значению число типа long double. Вам нужно обработать денежную строку как массив символов и, росматривая ее символ за символом, скопировать из нее только цифры (0-9) и десятичную точку в другую строку. Игнорируется все остальное, включая знак доллара и запятые. Затем вы можете использовать библиотечную функцию _atold() (заметим, что здесь название функции начинается с символа подчеркивания - заголовочные файлы STDLIB.H или MATH.H) для преобразования новой строки к числу типа long double. Предпологаем, что денежное значение не может быть отрицательным. Напишите функцию main() для проверки метода mstold(), которая несколько раз получаетс денежную строку от пользователя и выводит соответствующее число типа long double.
Пользуюсь Microsoft Visual Studio 2010 там такой "_atold()" функции нет. Пробовал "atof()" но она не работает с большими значениями типа "123456789.99", пробовал свою кустарную подобную функцию, результат был таким же. Есть какое то другое решение этой старой задачи?
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
#include<iostream>
using namespace std;
class money
{
private:
    long double mon;
public:
    long double mstold(char a[])
    {
        long double tmp=0;
        long double n=0,t=1;
        bool c=0;
        for(int i=0;i<strlen(a)+2;i++)
        {
            if(a[i]=='0'||a[i]=='1'||a[i]=='2'||a[i]=='3'||a[i]=='4'||a[i]=='5'||a[i]=='6'||a[i]=='7'||a[i]=='8'||a[i]=='9')
            {
                if(n!=0)
                    tmp=tmp*10+(a[i]-'0');
                if(n==0)
                {
                    tmp=tmp+(a[i]-'0');
                    n++;
                }
                if(c)
                    t*=10;
            }
            if(a[i]=='.')
                c=1;
        }
        return tmp/t;
    }
};
int main()
{
    setlocale(LC_ALL,"Rus");
    char str[50];
    money m;
    cout<<"Введите строку: ";
    cin>>str;
    long double t=m.mstold(str);
    cout<<"Вы ввели: "<<t<<endl;
    return 0;
}
0
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
19.09.2011, 16:14
Здравствуйте! Я подобрал для вас темы с ответами на вопрос Str в long double и наоборот (C++):

Как char[] перевести в битовую маску long long(64 бита) и наоборот? - C++
Как char перевести в битовую маску long long(64 бита) и наоборот?

Почему перестает работать программа при замене double на long double? - C++
Здравствуйте! Прошу помощи чтобы разобраться в следующем вопросе: Нашел программу в интернете, запустил - все работает, но когда решил...

long double и double в MSVC 12 одно и тоже, нужна информация,желательно быстрей - C++
Здравствуйте все знают что в VC long double и double одно и тоже, да и при простой проверке это легко выясняется, но нужна информация от...

Вывести long double число без перевода в double - C++
Надо вывести long double число без перевода в double. Пишу: printf(&quot;%Lf&quot;,S); и выводится неверно. Компилятор -- MinGW, та же фишка на...

Конвертирование из float в str и наоборот - C++
Приветствую всех! Господа, помогите освоить конвертацию типов. Знаю, что такие темы не раз поднимались, но прочитав их чего-то недопонял...

Double, int , long double - C++
Как вычислить диапазоны типов вручную указанных в название темы?

Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
ForEveR
В астрале
Эксперт С++
7972 / 4734 / 321
Регистрация: 24.06.2010
Сообщений: 10,541
Завершенные тесты: 3
19.09.2011, 16:38 #2
C++
1
2
boost::lexical_cast<long double>(str);
boost::lexical_cast<std::string>(some_double);
0
Sylvos
-25 / 6 / 1
Регистрация: 06.04.2011
Сообщений: 85
19.09.2011, 17:01  [ТС] #3
Это же вроде раздел для новичков, без дополнительных библиотек не как нельзя?
0
ForEveR
В астрале
Эксперт С++
7972 / 4734 / 321
Регистрация: 24.06.2010
Сообщений: 10,541
Завершенные тесты: 3
19.09.2011, 17:10 #4
Sylvos,
C++
1
2
3
std::istringstream ist(str);
long double value;
ist >> value;
C++
1
2
3
4
std::stringstream ss;
long double value = 1234567890123.99;
ss << value;
std::string str = ss.str();
Добавлено через 2 минуты
Если с точностью то так.

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
#include <string>
#include <iostream>
#include <sstream>
#include <iomanip>
 
int main()
{
   std::stringstream ss;
   long double value = 1234567890123.99;
   ss << std::fixed << std::setprecision(2) << value;
   std::string str = ss.str();
   std::cout << str << std::endl;
}
1
Sylvos
-25 / 6 / 1
Регистрация: 06.04.2011
Сообщений: 85
19.09.2011, 17:35  [ТС] #5
Я так понял что значения записывались правильно, только с выводом были проблемы?

Добавлено через 2 минуты
Вот мой исправленный код
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
#include<iostream>
#include <string>
#include <sstream>
#include <iomanip>
using namespace std;
class money
{
private:
    long double mon;
public:
    long double mstold(char a[])
    {
        long double tmp=0;
        long double n=0,t=1;
        bool c=0;
        for(int i=0;i<strlen(a)+2;i++)
        {
            if(a[i]=='0'||a[i]=='1'||a[i]=='2'||a[i]=='3'||a[i]=='4'||a[i]=='5'||a[i]=='6'||a[i]=='7'||a[i]=='8'||a[i]=='9')
            {
                if(n!=0)
                    tmp=tmp*10+(a[i]-'0');
                if(n==0)
                {
                    tmp=tmp+(a[i]-'0');
                    n++;
                }
                if(c)
                    t*=10;
            }
            if(a[i]=='.')
                c=1;
        }       
        return tmp/t;
    }
};
int main()
{
    setlocale(LC_ALL,"Rus");
    char st[50];
    money m;
    cout<<"Введите строку: ";
    cin>>st;
    long double t=m.mstold(st);
    stringstream ss;
    ss<<fixed<<setprecision(2)<<t;
    string str = ss.str();
    cout<<"Вы ввели: "<<str<<endl;
    return 0;
}
0
ForEveR
В астрале
Эксперт С++
7972 / 4734 / 321
Регистрация: 24.06.2010
Сообщений: 10,541
Завершенные тесты: 3
19.09.2011, 17:41 #6
Sylvos, Аха. Результат одинаковый.
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
#include <string>
#include <iostream>
#include <sstream>
#include <iomanip>
 
int main()
{
   std::string str("1234567890123.99");
   std::istringstream ss(str);
   long double value;
   ss >> value;
   std::cout << std::fixed << std::setprecision(2) << value << std::endl;
}
C++
1
2
3
4
5
6
7
8
9
10
11
#include <string>
#include <iostream>
#include <cstdlib> 
#include <iomanip>
 
int main()
{
   std::string str("1234567890123.99");
   long double value = atof(str.c_str());
   std::cout << std::fixed << std::setprecision(2) << value << std::endl;
}
0
odip
Эксперт С++
7157 / 3297 / 59
Регистрация: 17.06.2009
Сообщений: 14,164
20.09.2011, 09:32 #7
Вам нужно обработать денежную строку как массив символов и, росматривая ее символ за символом, скопировать из нее только цифры (0-9) и десятичную точку в другую строку. Игнорируется все остальное, включая знак доллара и запятые. Затем вы можете использовать библиотечную функцию _atold()
Честно говоря - зачем тебе функция atold() если ты уже разобрал массив ?
Можешь уже сам сделать преобразование, чем ты и занимаешься

К счастью, встроенный тип С++ long bouble имеет точность 19 цифр, плэтому мы можем использовать его как базисный для класса money, даже импользуя плавающую точку.
Кстати гонят они все !
Насколько я знаю вещественные не используют
Деньги требуют аккуратного счета, тип long double не годится из-за округления
0
Nameless One
Эксперт С++
5773 / 3424 / 255
Регистрация: 08.02.2010
Сообщений: 7,447
20.09.2011, 12:27 #8
Цитата Сообщение от odip Посмотреть сообщение
Насколько я знаю вещественные не используют
используют что-то типо такого:
http://speleotrove.com/decimal/decarith.html
0
Sylvos
-25 / 6 / 1
Регистрация: 06.04.2011
Сообщений: 85
20.09.2011, 14:15  [ТС] #9
Цитата Сообщение от odip Посмотреть сообщение
Честно говоря - зачем тебе функция atold() если ты уже разобрал массив ?
Можешь уже сам сделать преобразование, чем ты и занимаешься


Кстати гонят они все !
Насколько я знаю вещественные не используют
Деньги требуют аккуратного счета, тип long double не годится из-за округления
та это я по Лафоре Р. ООП в С++ 4 издание делаю задания, там еще куда глупее бывают примеры
0
Gepar
1177 / 533 / 20
Регистрация: 01.07.2009
Сообщений: 3,517
20.09.2011, 14:39 #10
Sylvos, почему сразу глупее примеры, преобразование данных из строки в int/double это классика, они, наверное, во всех самоучителях по с++ есть.
Пара комментариев по коду:

Цитата Сообщение от Sylvos Посмотреть сообщение
if(a[i]=='0'||a[i]=='1'||a[i]=='2'||a[i]=='3'||a[i]=='4'||a[i]=='5'||a[i]=='6'||a[i]=='7'||a[i]=='8'||a[i]=='9')
C++
1
if (isdigit(a[i]))
или ещё если очень хочется самому прописать условие то можно ещё
C++
1
if(a[i]>=48 && a[i]<=57)
48-57, как Вы уже догадались это коды символов 0-9, но предпочтительнее и нагляднее первый вариант с isdigit() всё же.

Цитата Сообщение от Sylvos Посмотреть сообщение
setlocale(LC_ALL,"Rus");
Сработает не всюду, лучше использовать вариант
C++
1
2
 SetConsoleCP(1251);
 SetConsoleOutputCP(1251);
0
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
20.09.2011, 14:39
Привет! Вот еще темы с ответами:

Long Double - C++
Разве нет типа более емкого, чем Double в Visual studio? Long Double, как я понял, определяется как обычный Double. А мне нужен аналог по...

Long float и double - C++
В чем отличие long float от double?

Округление Long double. - C++
Нужно округлить число типа long double в меньшую сторону т.е. просто обнулить всю дробную часть, но при этом надо сохранить эту самую...

long double и char - C++
Товарищи, помогите чайнику разобраться в данном теоретическом вопросе: long double* m=95; m--; m=? char* t=2; t-=4; t=?


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
Yandex
Объявления
20.09.2011, 14:39
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2017, vBulletin Solutions, Inc.
Рейтинг@Mail.ru