Уже несколько недель я пытаюсь перевести эту простую на вид функцию в дротик. У меня функция работает в Dart, но возвращает неправильный результат. Я пробовал разные варианты и стратегии, чтобы найти то, что идет не так. Я просто понятия не имею о VBA, поэтому это сложно. Может быть, если бы я мог поместить операторы печати в код VBA и посмотреть, что печатается на каждом этапе, тогда, возможно, я мог бы сделать дальнейшие выводы, но я понятия не имею, как это сделать или как читать операторы печати (например, где я могу их прочитать?) . Может ли кто-нибудь помочь мне попытаться понять это или помочь мне со стратегиями отладки? Моя последняя попытка состояла в том, чтобы просто использовать обычные функции Excel и использовать ячейки для хранения значений, и окончательный результат был точно таким же, как и в Dart! Так что это еще больше запутывает вещи. Я знаю, что код VBA дает правильный ответ, потому что в книге с фактическими математическими функциями говорится, что коды VBA дают правильный результат, но код Dart (и, по-видимому, просто попытка использовать обычные функции и ячейки Excel) дает неправильный результат.
Вот код VBA:
Function CND(X As Double) As Double
Dim y As Double, Exponential As Double, SumA As Double, SumB As Double
y = Abs(X)
If y > 37 Then
CND = 0
Else
Exponential = Exp(-y ^ 2 / 2)
If y < 7.07106781186547 Then
SumA = 3.52624965998911E-02 * y + 0.700383064443688
SumA = SumA * y + 6.37396220353165
SumA = SumA * y + 33.912866078383
SumA = SumA * y + 112.079291497871
SumA = SumA * y + 221.213596169931
SumA = SumA * y + 220.206867912376
SumB = 8.83883476483184E-02 * y + 1.75566716318264
SumB = SumB * y + 16.064177579207
SumB = SumB * y + 86.7807322029461
SumB = SumB * y + 296.564248779674
SumB = SumB * y + 637.333633378831
SumB = SumB * y + 793.826512519948
SumB = SumB * y + 440.413735824752
CND = Exponential * SumA / SumB
Else
SumA = y + 0.65
SumA = y + 4 / SumA
SumA = y + 3 / SumA
SumA = y + 2 / SumA
SumA = y + 1 / SumA
CND = Exponential / (SumA * 2.506628274631)
End If
End If
If X > 0 Then CND = 1 - CND
End Function
Вот функция Dart:
double cnd (double x) {
double y;
double exponential;
double sumA;
double sumB;
double value;
y = x.abs();
if (y > 37) {
value = 0;
} else {
exponential = exp(pow(-y, 2) / 2);
if (y < 7.07106781186547) {
sumA = 3.52624965998911E-02 * y + 0.700383064443688;
sumA = sumA * y + 6.37396220353165;
sumA = sumA * y + 33.912866078383;
sumA = sumA * y + 112.079291497871;
sumA = sumA * y + 221.213596169931;
sumA = sumA * y + 220.206867912376;
sumB = 8.83883476483184E-02 * y + 1.75566716318264;
sumB = sumB * y + 16.064177579207;
sumB = sumB * y + 86.7807322029461;
sumB = sumB * y + 296.564248779674;
sumB = sumB * y + 637.333633378831;
sumB = sumB * y + 793.826512519948;
sumB = sumB * y + 440.413735824752;
value = exponential * (sumA / sumB);
} else {
sumA = y + 0.65;
sumA = y + 4 / sumA;
sumA = y + 3 / sumA;
sumA = y + 2 / sumA;
sumA = y + 1 / sumA;
value = exponential / (sumA * 2.506628274631);
}
}
if (x > 0) {
value = 1 - value;
}
return value;
}
Вот скриншот Excel моей попытки использовать только функции и ячейки Excel:
Код =CND(-0.3253)
возвращает в Excel с кодом VBA. В Dart код cnd(-0.3253);
возвращает 0,4140535951706531, что является тем же результатом, который дает представление функции в Excel, показанное на изображении. Что происходит?
Да спасибо. Это была проблема с функцией pow!
Если результат VBA правильный, ваш код Dart, вероятно, должен выглядеть так:
exponential = exp(-pow(y, 2) / 2);
Я не могу тебя отблагодарить. Вы просто изменили мою жизнь! Я надеюсь, что ваша жизнь будет благословлена!
Не знаком с Dart, но в VBA возведение в степень имеет более высокий приоритет, чем отрицание, поэтому
-10^2/2
=>-50
. Скорее всего, функция Dartpow
будет эквивалентна VBA(-10)^2/2
=>+50