Форум программистов, компьютерный форум, киберфорум
Visual Basic
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.68/37: Рейтинг темы: голосов - 37, средняя оценка - 4.68
5 / 5 / 0
Регистрация: 07.04.2010
Сообщений: 328

Глюки VB - точность вычислений (Single, Double)

03.07.2010, 08:41. Показов 7827. Ответов 14
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Знатоки VB, подскажите, пожалуйста. Периодически возникает проблема когда работаешь со переменными типа SINGLE или DOUBLE при вычислении значений, например A=B/2-C/4, где переменные A,B,C одного из вышеуказанных типов при значениях B=3.6 и C=7.2 математически получается А=3.6/2-7.2/4=0, но VB выдает А=0.00000000000000068764 и или аналогичный бред и последующее сравнение значения А с нулем не выполняется. При пошаговом выполнении (debug) VB четко показывает, что B=3.6 и C=7.2 без каких либо долей, но результат 0.00000000000000068764 !!!!!!!!! ПОЧЕМУ ?????
0
cpp_developer
Эксперт
20123 / 5690 / 1417
Регистрация: 09.04.2010
Сообщений: 22,546
Блог
03.07.2010, 08:41
Ответы с готовыми решениями:

Глюки VB 2 - точность вычислений (Single, Double)
Добрый день как правильно объявить переменную делимого? Почему правильное объявление переменной ведет к неправильному результату? ...

Точность вычислений у double
Дана задача: "Определить, на сколько нулей заканчивается факториал числа n". Пример: вводим "25", на выходе должны получить...

Точность вычислений в double (Обрезание числа)
Здравствуйте! Дело в том, что мне необходимо выводить большие числа с большим количеством знаков после запятой. Однако и double и float...

14
6644 / 1511 / 169
Регистрация: 09.01.2010
Сообщений: 4,298
03.07.2010, 09:25
покажите фрагмент кода
0
 Аватар для Alex77755
11525 / 3812 / 683
Регистрация: 13.02.2009
Сообщений: 11,229
03.07.2010, 12:34
при просмотре при пошаговом выполнении a = 0
Visual Basic
1
2
Dim a As Double
 a = 3.6 / 2 - 7.2 / 4
0
6644 / 1511 / 169
Регистрация: 09.01.2010
Сообщений: 4,298
03.07.2010, 12:51
а должно быть сколько
0
 Аватар для Alex77755
11525 / 3812 / 683
Регистрация: 13.02.2009
Сообщений: 11,229
03.07.2010, 12:52
У автора
но VB выдает А=0.00000000000000068764
0
6644 / 1511 / 169
Регистрация: 09.01.2010
Сообщений: 4,298
03.07.2010, 13:01
у автора кажется 21 знак (0.00000000000000068764), это какой же тип допускает такое количество, если масштабируемое целое не поддерживается
0
 Аватар для Alex77755
11525 / 3812 / 683
Регистрация: 13.02.2009
Сообщений: 11,229
03.07.2010, 13:10
например такое:
тип данных Decimal
Тип данных для сохранения чисел в десятичном представлении с фактором масштабирования, равным степени 10. Без масштабирования, т.е. для целых чисел, допустимым диапазоном значений является +/-79*228*162*514*264*337*593*543*950*335. Для числа с 28 знаками в дробной части допустимым диапазоном значений является +/-7,9228162514264337593543950335. Минимальное ненулевое число, которое может быть представлено как значение типа Decimal, равняется 0,0000000000000000000000000001.
Добавлено через 7 минут
Сразу дополню(а то не все любят читать справку)

Необходимо помнить, что в настоящее время поддерживается использование типа Decimal только внутри типа Variant. Не допускается описание переменной с типом Decimal
. Пользователь, однако, имеет возможность, создать переменную типа Variant с подтипом Decimal с помощью функции CDec.
0
6644 / 1511 / 169
Регистрация: 09.01.2010
Сообщений: 4,298
03.07.2010, 13:51
вот так или как , что б в результатирующей было 28 зн.
Dim a As Variant
a = CDec(1 / 3)
Label1 = a
ну и речь идет о результате типа SINGLE или DOUBLE
0
5 / 5 / 0
Регистрация: 07.04.2010
Сообщений: 328
05.07.2010, 06:09  [ТС]
помещаю код

объявление переменных :
Visual Basic
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
DefDbl D
DefInt I, K
DefLng L
DefStr S
DefSng N, Q
Dim sf, shomedir As String
Dim kK, kn, kr, kvse, kmnu, kr1, kvnp, krkf As Integer
Dim iraschet As Integer 
Dim iris As Integer 
Dim kprint As Integer
Dim lraz As Long 
Dim lxmin, lxmax, lymin, lymax As Long 
Dim lbr As Long 
Dim lrazk 
Dim f(1 To 1000, 1 To 22) As Single
Dim s(1 To 1000) As String
Dim qd(1 To 1000, 1 To 7) As Single
Dim qgg(1 To 1000, 1 To 8) As Single
Dim kda(1 To 14) As Integer
Dim kch As Integer 
Dim kppr As Integer 
Dim kuso As Integer 
Dim kppr1 As Integer 
Dim ny, nmrs, nrb, nrbt As Single
Dim qpp, qm11, qm22, qt11, qt22 As Single 
Dim ikoa, ikob As Integer 
Dim qeb, qea, qmbs, qmas, qpn, qmb1, qma1, qmb2, qma2, qpmb, qpma, qpmx, qpmn As Single
Dim qdpmax, qdpmin, qdta, qdtb, qdma, qdmb, qd1, qd2, qd3, qd4, qd5, qd6, qd7, qatrans, qbtrans, qxx, qyy, qd66, qd77 As Single
Dim ltip(1 To 1000) As Long
Dim sot As String 
Dim nrra, nrra1, nl, ngmin11, nm, nq, nh0, na, nb, nsrh, nam, ner, nar As Single 
Dim iog As Integer 
Dim ipic(1 To 9) As Integer 
Dim nsh1 As Single 
Dim qm1, qt1, qm2, qt2, qp As Single 
Dim nsva1, nsva2, nsva3, nsva11, nsva12, nsva13, nsvb1, nsvb2, nsvb3, nsvb11, nsvb12, nsvb13, nh1, nh2, nh3 As Single
Dim nl1, nl11, nl2, nl12, nl3, nl13, nl4, nl14, nl5, nl15, nl6, nl16 As Single
Dim iprod, iprod1 As Integer 
Dim nkiom, nkioq, nkipm, nkipq, nkipp, nkir As Single
фрагмент кода
Visual Basic
1
2
3
4
If (na / 2 - nl4 - nl5 - f(iprod, 20) / 2000 + f(iprod, 22) / 1000) <=0 And nh3 <> 0 And (nb / 2 - nl1 - nl2 - f(iprod, 19) / 2000 + f(iprod, 21) / 1000) <=0 Then
MsgBox "Сообщение !", vbCritical, "Расчет фундамента"
iprod = iprod + 1
End If
Поясню, чтоб вам быстрее понять - не получается равным нулю результат сложений и вычитаний в общей скобке, который потом сравнивается <=0.
В выше указанном коде при пошаговом выполнении переменные и элементы массива имеют конкретные значения заданные пользователем. Точность этих чисел не более двух знаков после запятой. При пошаговом выполнении программы на этой строке кода деббагер дает именно те значения, что ввел пользователь и расчет на калькуляторе дает результат ноль, но VB!!!!, чтоб меня, дает кучу нулей после запятой и еще какие-нибудь цифры и проверка =0 не срабатывает, приходиться тупа писать вышеуказанный код по другому, чтобы обойти этот глюк :
Visual Basic
1
2
3
4
If (na / 2 - nl4 - nl5 - f(iprod, 20) / 2000 + f(iprod, 22) / 1000) < 0.001 And nh3 <> 0 And (nb / 2 - nl1 - nl2 - f(iprod, 19) / 2000 + f(iprod, 21) / 1000) < 0.001 Then
MsgBox "Сообщение !", vbCritical, "Расчет фундамента"
iprod = iprod + 1
End If
В моем первом сообщении количество нулей считать не нужно, я набил их много, чтобы показать принцып, а не точное количество знаков после запятой. Вообще эта проблема меня периодически беспокоит и уже порядком задолбала. Спасибо кто откликнулся.

Добавлено через 33 минуты
ЕЩЕ КОРОЧЕ !!!!!!!!

Запусьтите у себе вот этот код:
Visual Basic
1
2
3
4
5
6
7
8
9
10
11
12
13
Dim f(1 To 1000, 1 To 22) As Single
Dim na As Single
Dim nl4, nl5 As Single
Dim iprod As Integer
 
Private Sub Command1_Click() ' щелкаем по кнопочке
na = 3.3: nl4 = 0.75: nl5 = 0.6: iprod = 1: f(iprod, 20) = 600: f(iprod, 22) = 0
If (na / 2 - nl4 - nl5 - f(iprod, 20) / 2000 + f(iprod, 22) / 1000) = 0 Then
MsgBox "Сообщение !", vbCritical, "Расчет фундамента"
iprod = iprod + 1
End If
 
End Sub
У МЕНЯ СООБЩЕНИЕ (MsgBox "Сообщение !", vbCritical, "Расчет фундамента") НЕ ПОЯВЛЯЕТСЯ !!!!!! А У ВАС ???????????
0
5 / 5 / 0
Регистрация: 07.04.2010
Сообщений: 328
05.07.2010, 06:15  [ТС]
Смотрите на картинке (вложение), что показывает VB !!
Миниатюры
Глюки VB - точность вычислений (Single, Double)  
0
 Аватар для Alex77755
11525 / 3812 / 683
Регистрация: 13.02.2009
Сообщений: 11,229
05.07.2010, 07:05
Dim na As Single убери As Single
оставь просто
Dim na
почему я не всегда объявляю тип переменных...
0
5 / 5 / 0
Регистрация: 07.04.2010
Сообщений: 328
05.07.2010, 08:22  [ТС]
Цитата Сообщение от Alex77755 Посмотреть сообщение
Dim na As Single убери As Single
оставь просто
Dim na
почему я не всегда объявляю тип переменных...
почему я должен убирать объявление типа переменной ???
Тем более, что это ничего не дает, сообщение все равно не появляется ???
0
 Аватар для Alex77755
11525 / 3812 / 683
Регистрация: 13.02.2009
Сообщений: 11,229
05.07.2010, 08:59
Да действительно глюк
А я проверил только первую строчку:

Debug.Print na / 2 - nl4 - nl5, f(iprod, 20) / 2000
В дебаггере 0,3 0,3
А когда написал вторую
Debug.Print na / 2 - nl4 - nl5 - f(iprod, 20) / 2000
В дебаггере -5,55111512312578E-17
но эти 0,3 не одинаковые. Даже
Visual Basic
1
If (na / 2 - nl4 - nl5) = (f(iprod, 20) / 2000) Then na = na
не срабатывает
помогло только :
Visual Basic
1
2
Debug.Print CDec(na / 2 - nl4 - nl5) - CDec(f(iprod, 20) / 2000)
If (CDec(na / 2 - nl4 - nl5) - CDec(f(iprod, 20) / 2000) + f(iprod, 22) / 1000) = 0 Then
0
5 / 5 / 0
Регистрация: 07.04.2010
Сообщений: 328
05.07.2010, 09:29  [ТС]
Так тоже можно. Но ведь этот вопрос надо решить глобально, чтоб каждый раз не мудохаться. В чем собака зарыта ??? Это ГЛЮК или что-то делаем не так ????? И главное это глюк скрытый, он появляется только при тщательной отладке, а если его не обнаружить, то прога может работать некорректно - неприятно очень !!!

Добавлено через 17 минут
Visual Basic
1
2
3
4
5
6
Private Sub Command1_Click() 
If 1.65 - 0.75 - 0.6 - 0.3 = 0 Then
MsgBox "Сообщение !", vbCritical, "ГЛЮК"
End If
 
End Sub
ВООБЩЕ БРЕД, ДАЖЕ ТАК НЕ СРАБАТЫВАЕТ !!!!!
0
6644 / 1511 / 169
Регистрация: 09.01.2010
Сообщений: 4,298
05.07.2010, 11:26
в результате операций , проводимых с переменными этого типа, могут возникать ошибки округления
как вариант,
1. округлять результат до приемлемой точности (Alex77755 выше предлагал)
2 или (что в принципе то же самое) сравнивать не с 0 , а с , например, 0,000001
3 использовать FormatNumber
Visual Basic
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
Private Sub Command1_Click()
If Abs(1.65 - 0.75 - 0.6 - 0.3) < 0.000001 Then
MsgBox "Сообщение !", vbCritical, "ГЛЮК"
End If
 
End Sub
 
Private Sub Command2_Click()
If Round((1.65 - 0.75 - 0.6 - 0.3), 5) = 0 Then
MsgBox "Сообщение !", vbCritical, "ГЛЮК"
End If
End Sub
 
Private Sub Command3_Click()
 
If FormatNumber(1.65 - 0.75 - 0.6 - 0.3, 4) = 0 Then
MsgBox "Сообщение !", vbCritical, "ГЛЮК"
End If
 
End Sub
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
raxper
Эксперт
30234 / 6612 / 1498
Регистрация: 28.12.2010
Сообщений: 21,154
Блог
05.07.2010, 11:26
Помогаю со студенческими работами здесь

Точность Single
Такая проблема: конвертирую StrToFloat в Single, при этом теряется точность, число округляется до целых, если учесть, что это геодезические...

точность вычислений
Известно что в Питоне: 1.001 + 5 = 6.0009999999999994 А хочется чтобы было 6.001 Пользователь хочет видеть красивые числа...

Точность вычислений
Для проверки точности вычислений существуют формулы и калькулятор на 200000 знаков до и после запятой. Проверяются любые вычисленные...

Точность вычислений
Здравствуйте уважаемые форумчане. Если в матлабе вычислить такое выражение 0.05+0.001 == 0.051 то он выдаст 0; А если...

Точность вычислений 10^30 - 10^(-30)
Здравствуйте, скажите пожалуйста, можно ли в какой либо программе, или на супер компьютере проводить вычисления примерно такого порядка...


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

Или воспользуйтесь поиском по форуму:
15
Ответ Создать тему
Новые блоги и статьи
SDL3 для Web (WebAssembly): Обработчик клика мыши в браузере ПК и касания экрана в браузере на мобильном устройстве
8Observer8 02.02.2026
Содержание блога Для начала пошагово создадим рабочий пример для подготовки к экспериментам в браузере ПК и в браузере мобильного устройства. Потом напишем обработчик клика мыши и обработчик. . .
Философия технологии
iceja 01.02.2026
На мой взгляд у человека в технических проектах остается роль генерального директора. Все остальное нейронки делают уже лучше человека. Они не могут нести предпринимательские риски, не могут. . .
SDL3 для Web (WebAssembly): Вывод текста со шрифтом TTF с помощью SDL3_ttf
8Observer8 01.02.2026
Содержание блога В этой пошаговой инструкции создадим с нуля веб-приложение, которое выводит текст в окне браузера. Запустим на Android на локальном сервере. Загрузим Release на бесплатный. . .
SDL3 для Web (WebAssembly): Сборка C/C++ проекта из консоли
8Observer8 30.01.2026
Содержание блога Если вы откроете примеры для начинающих на официальном репозитории SDL3 в папке: examples, то вы увидите, что все примеры используют следующие четыре обязательные функции, а. . .
SDL3 для Web (WebAssembly): Установка Emscripten SDK (emsdk) и CMake для сборки C и C++ приложений в Wasm
8Observer8 30.01.2026
Содержание блога Для того чтобы скачать Emscripten SDK (emsdk) необходимо сначало скачать и уставить Git: Install for Windows. Следуйте стандартной процедуре установки Git через установщик. . . .
SDL3 для Android: Подключение Box2D v3, физика и отрисовка коллайдеров
8Observer8 29.01.2026
Содержание блога Box2D - это библиотека для 2D физики для анимаций и игр. С её помощью можно определять были ли коллизии между конкретными объектами. Версия v3 была полностью переписана на Си, в. . .
Инструменты COM: Сохранение данный из VARIANT в файл и загрузка из файла в VARIANT
bedvit 28.01.2026
Сохранение базовых типов COM и массивов (одномерных или двухмерных) любой вложенности (деревья) в файл, с возможностью выбора алгоритмов сжатия и шифрования. Часть библиотеки BedvitCOM Использованы. . .
SDL3 для Android: Загрузка PNG с альфа-каналом с помощью SDL_LoadPNG (без SDL3_image)
8Observer8 28.01.2026
Содержание блога SDL3 имеет собственные средства для загрузки и отображения PNG-файлов с альфа-каналом и базовой работы с ними. В этой инструкции используется функция SDL_LoadPNG(), которая. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru