atan на ЧЕТЫРЁХ умножениях

Sep 14, 2021 21:37

Мишка такой человек - ему обязательно надо, чтоб от всего была польза. Когда у него бывают лишние деньги, он идёт в магазин и покупает какую-нибудь полезную книжку. Один раз он купил книгу, которая называется «Обратные тригонометрические функции и полиномы Чебышева». Конечно, он ни слова в этой книжке не понял и решил прочитать её потом, когда немножко поумнеет. С тех пор эта книга лежит у него на полке - ждёт, когда он поумнеет.
Николай Носов, "Весёлая семейка"

Пока не стал пытаться ещё сильнее оптимизировать коэффициенты для арктангенса на ДВУХ умножениях, поскольку подозреваю, что чудес не бывает - какие-то проценты ещё можно выжать, но мне бы хотелось повысить точность НА ПОРЯДОК. Так что, скрепя сердце, добавил ещё одно слагаемое и нашёл коэффициенты с помощью интерполяции по узлам Чебышёва.

Получил такой результат:



Напомню: мы имеем дело уже с отнормированным вектором, т.е x2+y2=1, и это офигительно упрощает дело! Плюс две формулы приведения, сначала к x≥0, затем к x≥|y|, т.е к углам от -45° до +45°.

В таких условиях данная формула даёт ошибку не более 4,9 угловой секунды! Этого более, чем достаточно для наших 16-битных вычислений, где цена младшего разряда углов составляет 12 угловых секунд.

График ошибки:



И в отличие от того нашего алгоритма с поворотами комплексных чисел, тут и вычислительных ошибок может набраться сильно меньше, за счёт 32-битного аккумулятора и "байпаса".


Код, непосредственно реализующий эту формулу, выглядит примерно так:

SQRD2 [X+1]
C AtanGamma
MUL Acc
C AtanBeta
FMA [X+k]
ADD AtanAlpha
C [X+1]
MUL UAC

В первой строчке y возводится в квадрат, и 32-битный результат лежит в аккумуляторе.

В строке "MUL Acc" срабатывает "байпас", дополнительная шина, соединяющая младшие биты входа и выхода АЛУ. Благодаря нему, в умножении задействованы практически все 32 бита результата, что повышает точность.

Строка "FMA [X+k]" также хороша: это Fused Multiply-Add. Не зря я назвал её так, а не MAC (Multiply-Accumulate). Разница как раз в том, что FMA способна использовать аккумулятор большой ширины и продолжать накапливать в нём выражение с полной точностью.

И в самом конце, "MUL UAC", байпас срабатывает ещё разок. Вместо Acc тут используется UAC (Unsigned Acc), поскольку в скобке значение будет больше единицы, и ни в коем случае нельзя здесь вызывать "насыщение".

Наверное, так в итоге и сделаю. Ну, ещё сейчас надо глянуть, не слишком ли криво формулы приведения ложатся, надеюсь, что как-нибудь ляжет, может прям через i^k и регистр Inv, они же позволяют поменять два значения местами "виртуально", а также знаки поменять, не прибегая к убийственным ветвлениям... Забавно, как старая реализация, практически дошедшая до железа, устарела ещё до того, как хоть раз заработала. А всё потому, что МИША ПОУМНЕЛ.

Ещё забавно, что на вычислительной математике, на втором курсе, нам рассказывали, что интерполировать иногда лучше не через равные интервалы, а по узлам Чебышёва, но не стали особенно подчёркивать факт, НАСКОЛЬКО ЭТО КРУЧЕ! Даже тот пример, что был там приведён, оказывался каким-то беззубым - там что в лоб, что по лбу - примерно одно и то же получалось. Ну ладно, лучше поздно, чем никогда :)

странные девайсы, математика, ПЛИС, программки, работа, Книги

Previous post Next post
Up