Страница: 1 | 2 |
Вопрос: Проблема с QBasic'ом
Добавлено: 22.03.07 08:48
Автор вопроса: true4u
Здравствуйте.
Хотелось бы получить от Вас помощь по такому вопросу:
---------
Проявилась небольшая "гадость" при работе с Бейсиком. Раньше с таким ни разу не сталкивался!!!
Смотрите пример двух программ организации перебора числа: а) счетчик в цикле, б)постепенное приращенеи значения переменной.
Под кажой программой даны результаты ее работы.
Программа а):
'------------------------
FOR a = 1 TO 3 STEP .1
PRINT a
NEXT a
'------------------------
Результаты программы а):
1
1.1
1.2
1.3
1.4
1.5
1.6
1.7
1.8
1.9
2
2.1
2.2
2.3
2.4
2.5
2.6
2.7
2.799999
2.899999
2.999999
или
Программа б):
'------------------------
n=1
FOR a = 1 TO 20
PRINT n
n=n+.1
NEXT a
'------------------------
Результаты программы б):
1
1.1
1.2
1.3
1.4
1.5
1.6
1.7
1.8
1.9
2
2.1
2.2
2.3
2.4
2.5
2.6
2.7
2.799999
2.899999
***********************
А в результате верного выполнения должны быть числа: 1, 1.1, 1.2, ... , 2.5, 2.6, 2.7, 2.8, 2.9 (т.е. числа идут с шагом 0.1 и после запятой только одна цифра!!!)
Как видно из результатов, Бейсик мудрит с вещественными числами и, вместо того чтобы прибавлять просто 0.1, он прибавляет что-то другое (очевидно с какой-то точностью!!!).
---------
Вы знаете как с этим можно бороться?
Получается просто сложить несколько чисел (десяток), равных 0.1, без ошибки в Бейсике НЕЛЬЗЯ??? Или можно с этим как-то бороться???
Спасибо!
С уважением,
Владимир.
Ответы
Всего ответов: 28
Номер ответа: 1
Автор ответа:
VoVaN
ICQ: 4921085
Вопросов: 27
Ответов: 38
Профиль | | #1
Добавлено: 22.03.07 08:50
округлять до нужного количества знаков
Номер ответа: 2
Автор ответа:
true4u
Вопросов: 2
Ответов: 15
Профиль | | #2
Добавлено: 22.03.07 08:54
Есть ли специальный оператор для этой цели? Или надо писать свою подпрограмму?
Номер ответа: 3
Автор ответа:
true4u
Вопросов: 2
Ответов: 15
Профиль | | #3
Добавлено: 22.03.07 08:55
Есть ли специальный оператор для этой цели? Или надо писать свою подпрограмму?
Номер ответа: 4
Автор ответа:
VoVaN
ICQ: 4921085
Вопросов: 27
Ответов: 38
Профиль | | #4
Добавлено: 22.03.07 08:58
есть. в VB это ROUND(число, число_знаков). На QB тоже должен быть
Номер ответа: 5
Автор ответа:
true4u
Вопросов: 2
Ответов: 15
Профиль | | #5
Добавлено: 22.03.07 09:19
В QB такого нет!
Но округление - это только одна ошибка!
-------
Вторая - счетчик цикла!!!
Получается, что цикл с вещественным шагом
FOR a = 1 TO 3 STEP .1
PRINT a
NEXT a
НЕЛЬЗЯ организовать без ошибочого вычисления счетчика цикла???
Номер ответа: 6
Автор ответа:
Viper
ICQ: 249094859
Вопросов: 0
Ответов: 310
Профиль | | #6
Добавлено: 22.03.07 10:18
еще один... откуд беруцца тока? Вещественные числа в цикле это зло само по себе. Ну и до кучи, вещественные числа не обеспечиваю точного представления числа по своей природе. Во избежание ненужных инсинуаций добавлю, что это есть особенность реализации на уровне процессора, так что не стоит гнать бочку на VB (или в данном случае на QB) типа что сей язык плох, потому что не может работать с вещественными числами.
Совет по теме: в цикле пользовать целые числа, вещественные же при выводе округлять до нужного значения. Еще лучше юзать Currency (если этот тип поддерживается в QB)
Номер ответа: 7
Автор ответа:
true4u
Вопросов: 2
Ответов: 15
Профиль | | #7
Добавлено: 22.03.07 11:01
1. Тока беруцца из напряжения и сопротивления.
2. Бочки никто не упоминал.
3. Currency в QB нет.
4. Счетчик цикла - целое число; в самом цикле просто последовательное суммирование.
n=1
FOR a = 1 TO 20
PRINT n
n=n+.1
NEXT a
результат:
1
1.1
1.2
1.3
1.4
1.5
1.6
1.7
1.8
1.9
2
2.1
2.2
2.3
2.4
2.5
2.6
2.7
2.799999
2.899999
Что здесь не так сделано?
5. Внимательнее читайте вопросы!!!
Номер ответа: 8
Автор ответа:
EROS
Вопросов: 58
Ответов: 4255
Профиль | | #8
Добавлено: 22.03.07 12:36
true4u,
Уважаемый.. эта тема поднималась на форуме десятки раз.. И единственное верное решение тебе уже сказали.. Используй округление.. другого решения нет. И дело вовсе не в том, что ты что то не так сделал а в особенностях реализации некоторых типов данных в VB
Номер ответа: 9
Автор ответа:
Viper
ICQ: 249094859
Вопросов: 0
Ответов: 310
Профиль | | #9
Добавлено: 22.03.07 15:29
Читай однако внимательнее ответы
Зацени конструкцию типа:
Dim i As Integer
Dim n As Single
For i = 1 To 20
n = 1# + 0.1 * i
Print n
Next i
Номер ответа: 10
Автор ответа:
true4u
Вопросов: 2
Ответов: 15
Профиль | | #10
Добавлено: 22.03.07 15:42
Viper'у:
Это работает еще проще:
For i = 1 To 20
n = i/10
Print n
Next i
Но это же МАРАЗМ!!! Кстати, это надо проверить на большом диапазоне! Возможно где-то опять проявится ошибка!!!
Номер ответа: 11
Автор ответа:
true4u
Вопросов: 2
Ответов: 15
Профиль | | #11
Добавлено: 22.03.07 15:42
А вот еще:
**********
Вот пример программы, входных данных и результата! Как я в ней могу контролировать точность введенных данных?
Получается, что БЕЙСИК НЕВЕРНО ВЫЧИСЛЯЕТ даже такие простые значения! А что он будет делать с "длинными" числами (много знаков после запятой!!!)??? Вообще ужас!!!
s = 0
FOR a = 1 TO 20
INPUT b
s = s + b
NEXT a
PRINT s
----------------------
? .1
? .1
? .1
? .1
? .1
? .1
? .1
? 1
? .1
? 1
? 1
? 1.1
? .1
? .1
? .1
? .1
? .1
? .1
? .1
? .1
5.699999
Номер ответа: 12
Автор ответа:
true4u
Вопросов: 2
Ответов: 15
Профиль | | #12
Добавлено: 22.03.07 15:48
Как хоть можно после этого верить...???
Номер ответа: 13
Автор ответа:
true4u
Вопросов: 2
Ответов: 15
Профиль | | #13
Добавлено: 22.03.07 16:11
...вычислениям в QB???!!!
Номер ответа: 14
Автор ответа:
Серёга
ICQ: 262809473
Вопросов: 17
Ответов: 561
Web-сайт:
Профиль | | #14
Добавлено: 22.03.07 20:46
true4u, есть один извратный способ для решения твоей проблемы:
n=1
FOR a = 1 TO 20
PRINT n
n=n+.1
n=val(str$(n))
NEXT a
но конечно тоже есть ограничения.
Номер ответа: 15
Автор ответа:
Sharp
Лидер форума
ICQ: 216865379
Вопросов: 106
Ответов: 9979
Web-сайт:
Профиль | | #15
Добавлено: 23.03.07 01:51
А есть один не извратный
for i=10 to 30
print i / 10
next