Я хотел бы расширить ответ, предоставленный @Jason S. Используя метод деления домена, аналогичный описанному в @Jason S, и используя приближения рядов Маклаурина, среднее (2-3) X ускорение по сравнению с tan (), Были достигнуты функции sin (), cos (), atan (), asin () и acos (), встроенные в компилятор gcc с оптимизацией -O3. Описанные ниже лучшие аппроксимирующие функции серии Маклаурина достигли двойной точности.
Для функций tan (), sin () и cos () и для простоты перекрывающийся домен от 0 до 2pi + pi / 80 был разделен на 81 равный интервал с «опорными точками» в pi / 80, 3pi / 80, ..., 161pi / 80. Затем tan (), sin () и cos () из этих 81 опорных точек были оценены и сохранены. С помощью идентификаторов триггеров для каждой функции триггера была разработана отдельная функция ряда Маклаурина. Любой угол между ± бесконечностью может быть передан в функции аппроксимации триггера, потому что функции сначала переводят входной угол в область от 0 до 2pi. Эти накладные расходы на перевод включаются в накладные расходы на приближение.
Подобные методы были разработаны для функций atan (), asin () и acos (), где перекрывающийся домен от -1,0 до 1,1 был разделен на 21 равный интервал с точками привязки в -19/20, -17/20 , ..., 19/20, 21/20. Тогда только atan () из этих 21 опорных точек был сохранен. Опять же, с помощью обратных тригогенных тождеств была разработана единственная функция ряда Маклаурина для функции atan (). Результаты функции atan () были затем использованы для аппроксимации asin () и acos ().
Поскольку все аппроксимирующие функции обратного триггера основаны на аппроксимирующей функции atan (), допускается любое входное значение аргумента двойной точности. Однако входной аргумент для аппроксимирующих функций asin () и acos () усекается до области ± 1, потому что любое значение вне его является бессмысленным.
Чтобы протестировать аппроксимирующие функции, пришлось оценить миллиард случайных оценок функций (т. Е. Оптимизирующему компилятору -O3 не разрешалось обходить оценку чего-либо, потому что некоторый вычисленный результат не будет использоваться). Чтобы удалить смещение оценивая миллиард случайных чисел и обрабатывая результаты, сначала выполнялась стоимость прогона без оценки какой-либо функции триггера или обратной функции триггера. Это смещение затем вычиталось из каждого теста, чтобы получить более представительную аппроксимацию фактического времени оценки функции.
Таблица 2. Время, потраченное в секундах на выполнение указанной функции или функции, составляет один миллиард раз. Оценки получены путем вычитания затрат времени на оценку одного миллиарда случайных чисел, показанных в первой строке таблицы 1, из оставшихся строк таблицы 1.
Время, проведенное в загар (): 18.0515 18.2545
Время, проведенное в TAN3 (): 5,93853 6,02349
Время, проведенное в TAN4 (): 6,72216 6.99134
Время, проведенное в грехе () и соз (): 19.4052 19.4311
Время, проведенное в SINCOS3 (): 7,85564 7,92844
Время, проведенное в SINCOS4 (): 9,36672 9,57946
Время, проведенное в atan (): 15.7160 15.6599
Время, проведенное в ATAN1 (): 6,47800, 6,55230
Время, проведенное в ATAN2 (): 7,26730 7,24885
Время, проведенное в ATAN3 (): 8.15299 8.21284
Время, проведенное в asin () и acos (): 36,8833 36,9496
Время, проведенное в ASINCOS1 (): 10.1655 9.78479
Время, проведенное в ASINCOS2 (): 10,6236 10,6000
Время, проведенное в ASINCOS3 (): 12,8430 12,0707
(В целях экономии места таблица 1 не показана.) В таблице 2 показаны результаты двух отдельных прогонов по миллиарду оценок каждой аппроксимирующей функции. Первый столбец - это первый прогон, а второй столбец - второй прогон. Числа «1», «2», «3» или «4» в названиях функций указывают количество терминов, используемых в функции рядов Макларина для оценки конкретного триггера или аппроксимации обратного трига. SINCOS # () означает, что и sin, и cos были вычислены одновременно. Аналогично, ASINCOS # () означает, что asin и acos были оценены одновременно. Существует небольшая дополнительная нагрузка при оценке обоих количеств одновременно.
Результаты показывают, что увеличение количества слагаемых немного увеличивает время выполнения, как и следовало ожидать. Даже наименьшее количество членов дает точность 12-14 цифр везде, за исключением приближения tan (), близкого к тому, где его значение приближается к бесконечности. Можно было бы ожидать, что даже у функции tan () возникнут проблемы.
Аналогичные результаты были получены на высококачественном ноутбуке MacBook Pro в Unix и на настольном компьютере высокого класса в Linux.