//by Rick Companje
//www.companje.nl
//18-11-2007
//more info
//* http://home.wanadoo.nl/rule-off/wis/reeksen.htm
//* http://lab.polygonal.de/
//* http://lab.polygonal.de/wp-content/articles/fast_trig/fastTrig.as
final float C1 = 4/PI;
final float C2 = 4/(PI*PI);
int time;
float qsinLow1(float x) {
//efficient maar minder nauwkeurig
//1856ms voor 100.000.000 aanroepen
return C1*x + (C2*x*x) * (x<0?1:-1);
}
float qsinLow2(float x) {
//efficient maar minder nauwkeurig
//hierbij wordt geen gebruik gemaakt van de constanten
//C1 en C2. Het scheel op 100.000.000.000 berekeningen
//een paar milliseconden en is echt verwaarloosaar.
//gebruik dus prima constanten (final float).
return 1.2732395*x + (0.4052847*x*x) * (x<0?1:-1);
}
float qsinHigh1(float x) {
//trager dan qsin1 maar een stuk nauwkeuriger
//3851ms voor 100.000.000 aanroepen
float sinX = qsinLow1(x);
return .225*((x<0?-1:1)*sinX*sinX-sinX)+sinX;
}
float qsinHigh2(float x) {
//niet efficient maar waarom? geen idee.
//8867ms voor 100.000.000.000
//het leek mij het overslaan van het aanroepen
//van qsin1 en in plaats daarvan de code inline
//uitvoeren voordelig zou moeten zijn maar integendeel.
float sinX = C1*x + (C2*x*x) * (x<0?1:-1);
return .225*((x<0?-1:1)*sinX*sinX-sinX)+sinX;
}
float qsinHigh3(float x) {
//snelste nauwkeurige benadering
//verwaarloosbaar sneller dan qsin2
float sinX = qsinLow2(x);
return .225*((x<0?-1:1)*sinX*sinX-sinX)+sinX;
}
float qsinHigh4(float x) {
//een stuk trager net als qsin3 door het juist
//niet aanroepen van qsin4. ik vind heet vreemd.
float sinX = 1.2732395*x + (0.4052847*x*x) * (x<0?1:-1);
return .225*((x<0?-1:1)*sinX*sinX-sinX)+sinX;
}
void setup() {
background(0);
size(400,400);
int maxi=100000000;
float result;
float x=PI;
delay(1000);
startTimer(); for (int i=0; i<maxi; i++) result = sin(x); stopTimer("sin");
startTimer(); for (int i=0; i<maxi; i++) result = qsinLow1(x); stopTimer("qsinLow1");
startTimer(); for (int i=0; i<maxi; i++) result = qsinLow2(x); stopTimer("qsinLow2");
startTimer(); for (int i=0; i<maxi; i++) result = qsinHigh1(x); stopTimer("qsinHigh1");
startTimer(); for (int i=0; i<maxi; i++) result = qsinHigh2(x); stopTimer("qsinHigh2");
startTimer(); for (int i=0; i<maxi; i++) result = qsinHigh3(x); stopTimer("qsinHigh3");
startTimer(); for (int i=0; i<maxi; i++) result = qsinHigh4(x); stopTimer("qsinHigh4");
//inline versie, lage nauwkeurigheid. Is het
//snelst bij lage nauwkeurigheid.
//kost 1233 voor 100.000.000.000 aanroepen.
startTimer();
for (int i=0; i<maxi; i++) result = 1.2732395*x + (0.4052847*x*x) * (x<0?1:-1);
stopTimer("inline low");
//inline versie, hoge nauwkeurigheid.
//Is snelst bij hoge nauwkeurigheid
//kost 2818 voor 100.000.000.000 aanroepen.
startTimer();
float sinX;
for (int i=0; i<maxi; i++) {
sinX = 1.2732395*x + (0.4052847*x*x) * (x<0?1:-1);
result = .225*((x<0?-1:1)*sinX*sinX-sinX)+sinX;
}
stopTimer("inline high");
}
void startTimer() {
time = millis();
}
void stopTimer(String descr) {
println(descr + ": " + (millis()-time));
}
======Resultaat========
sin: 23232
qsinLow1: 1436
qsinLow2: 1421
qsinHigh1: 3195
qsinHigh2: 7443
qsinHigh3: 3154
qsinHigh4: 7532
inline low: 1233
inline high: 2818