Laat je niet van de wijs brengen door alle wiskundige formules.
Je kan afgeleiden en integralen:
- ofwel zelf uitrekenen (zoals je hierboven met wnvl gedaan hebt)
- ofwel opzoeken (in boeken of in een rekenomgeving zoals WolframAlpha)
Wiskundigen verkiezen meestal de eerste optie, programmeurs de tweede.
De oplossingsstrategie voor jouw probleem loopt dan via de volgende stappen:
[1] bepaal een parametervoorstelling van de spiraal: x en y-waarde als functie van t
[2] bepaal een formule voor de lengte s van de spiraal: s als functie van t
[3] zoek de inverse functie hiervan: t als functie van s
[4] bepaal voor elke stap s via [3] de waarde van t en met t via [1] de waarden van x en y
[1] bepaal een parametervoorstelling van de spiraal: x en y-waarde als functie van t
De standaard parametervoorstelling van een cirkel met middelpunt de oorsprong en straal r is:
\(x(t) = r \cdot cos(\theta)\)
\(y(t) = r \cdot sin(\theta)\)
met hoek theta een reeel getal.
Als theta loopt van 0 tot 2pi loopt de cirkel tegen de wijzers van de klok in van
punt (r,0) via (0,r), (-r,0) en (0,-r) terug naar (r,0).
Theta mag elk reeel getal zijn: als theta = 4pi heb je de cirkel 2 keer doorlopen,
bij 6pi 3 keer etc.
Je kan theta ook vervangen door 2pi*t, met t een reeel getal.
\(x(t) = r \cdot cos(2\pi t)\)
\(y(t) = r \cdot sin(2\pi t)\)
Als t=0 is theta=0, als t=1 is theta=2pi etc
Hier geeft t dus het aantal keren aan dat de cirkel doorlopen is.
Nu wil jij niet beginnen in (r,0), maar in (-r,0).
De draairichting blijft tegen de klok in, dus de parametervoorstelling wordt:
\(x(t) = -r \cdot cos(2\pi t)\)
\(y(t) = -r \cdot sin(2\pi t)\)
Bovendien wil je geen cirkel, maar een spiraal, waarvan de straal begint met
150 eenheden en geleidelijk afneemt met 30 eenheden per volledige rotatie, ofwel,
ook uitgedrukt in t:
r = 150 - 30*t
Vul dit in in de formules voor x en y:
\(x(t) = -(150 - 30\cdot t) \cdot cos(2\pi t)\)
\(y(t) = -(150 - 30\cdot t) \cdot sin(2\pi t)\)
of iets algemener met:
b = beginwaarde van de straal = 150
a = afname van de straal per rotatie = 30
\(x(t) = -(b - a\cdot t) \cdot cos(2\pi t)\)
\(y(t) = -(b - a\cdot t) \cdot sin(2\pi t)\)
ofwel:
\(x(t) = (a\cdot t - b) \cdot cos(2\pi t)\)
\(y(t) = (a\cdot t - b) \cdot sin(2\pi t)\)
Dit is de parametervoorstelling van je spiraal.
Parameter t loopt in ons geval van 0 (r=150) t/m 5 (r=0).
Als je bijvoorbeeld in een programma
voor t = 0 tot 5 met stapgrootte 0.01
punt (x(t), y(t)) berekent en plot
zou je spiraal al zichtbaar moeten worden.
@wnvl: volgens mij spiraliseer jij naar buiten ipv naar binnen
[2] bepaal een formule voor de lengte s van de spiraal: s als functie van t
De booglengte van een kromme bij gegeven parametervoorstelling hebben jullie bepaald
via deze weg:
http://nl.wikipedia.org/wiki/Booglengte
Zowel de twee afgeleiden (dx/dt en dy/dt) als de integraal kan je opzoeken
via bv WolframAlpha.
Je komt dan uit op:
\(s = \int_{t1}^{t2} \sqrt{\left(\frac{dx}{dt}\right)^2 + \left(\frac{dy}{dt}\right)^2}dt =\)
\(\left[\frac{at-b}{2a}\sqrt{(2\pi (at-b))^2 + a^2} + \frac{a}{4\pi}\ln \left( \sqrt{(2\pi (at-b))^2 + a^2}+2\pi (at-b)\right) \right]_{t1}^{t2}\)
Wij willen de booglengte s weten gemeten vanaf het beginpunt tot aan een bepaalde waarde t,
dus van t1=0 tot t2=t.
Dit levert met bovenstaande formule:
\(s = \frac{at-b}{2a}\sqrt{(2\pi (at-b))^2 + a^2} + \frac{a}{4\pi}\ln \left( \sqrt{(2\pi (at-b))^2 + a^2}+2\pi (at-b)\right) -\)
\(\left( \frac{a\cdot 0-b}{2a}\sqrt{(2\pi (a\cdot 0-b))^2 + a^2} + \frac{a}{4\pi}\ln \left( \sqrt{(2\pi (a\cdot 0-b))^2 + a^2}+2\pi (a\cdot 0-b)\right) \right)\)
Tot zover waren jullie gekomen.
Het is niet moeilijk dit om te zetten naar code, bv in C:
Code: Selecteer alles
//globale variabelen:
double spiral_a, spiral_b, spiral_t0;
//bereken booglengte:
double spirallength(double t)
{
double length,r,pr,w;
r = spiral_a * t - spiral_b;
pr = 2*pi*r;
w = sqrt(pr*pr+spiral_a*spiral_a);
length = r*w/(2*spiral_a);
length += spiral_a*log(w+pr)/(4*pi);
length -= spiral_t0;
return(length);
}
//definieer b, a en t0:
void initspiral(double b, double a)
{
spiral_b=b;
spiral_a=a;
spiral_t0 = 0;
spiral_t0 = spirallength(0);
}
initspiral(b,a) roep je 1 keer aan om je spiraal te definieren, daarna kan je voor
elke waarde van t met spirallength(t) de lengte van het spiraaldeel berekenen.
We hadden al gezien dat t loopt van 0 t/m 5, wat vind je zo voor de waarden van
spirallength(0.0)
en
spirallength(5.0)
?
[3] zoek de inverse functie: t als functie van s
Zie je een mogelijkheid om met behulp van de functie spirallength(t) een functie
spiral_s2t(s) te bouwen, die voor gegeven s (met bv nauwkeurigheid delta=0.0001)
de bijbehorende waarde van t efficient kan zoeken?
[4] bepaal voor elke stap s via [3] de waarde van t en met t via [1] de waarden van x en y
Het zal nu niet moeilijk zijn voor elke s met stapgrootte 10 de waarde van t te bepalen
en daarmee de waarde van x(t) en y(t) om die vervolgens op te slaan in een bestand of
de punten (x(t), y(t)) te plotten op een bitmap.