Подходящее округление Фортрана в C # - PullRequest
1 голос
/ 29 октября 2008

FORTRAN предоставляет несколько функций для преобразования числа с двойной точностью в целое значение. Метод, используемый для усечения / округления, отличается. Я конвертирую сложные научные алгоритмы, которые используют их.

Согласно документации FORTRAN:
aint (x) возвращает целое значение между x и 0, ближайшим x.
anint (x) возвращает ближайшее целое значение x, кроме случаев, когда на полпути округляется до целого значения, большего по величине.
nint (x) преобразует x в округление формата int до ближайшего значения int, кроме полпути округляются до значения int, большего по величине.

У кого-нибудь есть реализация этого в C #? Это может быть сложно сделать это правильно.

(int) x соответствует aint ()
Convert.ToInt32 (x) не соответствует ни одному из перечисленных.
Trunc (x) не соответствует ни одному из вышеперечисленных.
Round (x) может соответствовать anint или nint.

Разница между anint и nint, по-видимому, является типом возврата, где anint возвращает значение двойной точности, а nint возвращает целое число. Используются оба (острый образец):
ДВОЙНАЯ ТОЧНОСТЬ A, B, C, D, E, F, G
... значения, установленные здесь ...
F = ANINT (A-B) + ANINT (C-D) + ANINT (B + D-E)
G = NINT (F) + 1D0;
Возможно, эксперт ФОРТРАН мог бы помочь прояснить, почему автор решил использовать оба (я предполагаю, что это было преднамеренно).

Ответы [ 3 ]

3 голосов
/ 29 октября 2008

По вашим определениям вызовов nint и anint предоставляются Math.Round с использованием MidpointRounding.AwayFromZero.

Для aint явное приведение от double до int достигнет этого результата.

1 голос
/ 29 октября 2008

Из того, что я вижу, aint() - это просто Math.Floor().

Что касается двух других, я думаю, что вы правы, единственное отличие заключается в типе возвращаемого значения: nint() возвращает действительное целое число, а anint() возвращает двойное (fortran: real), которое оказывается целым значением.

0 голосов
/ 02 июля 2013

У меня есть реализация функции anint, следуйте коду:

double anint(double x)
{
    int a;
    double y;

    a = (int)x; //a=9

    if (10 * x - 10 * (double)a >= 5)
    {
        a = a + 1;
    }

    y = (double)a;

    return y;
}
...