|
You last visited: Today at 22:58
Advertisement
Phytagoras ohne math.h
Discussion on Phytagoras ohne math.h within the C/C++ forum part of the Coders Den category.
01/08/2013, 06:55
|
#1
|
elite*gold: 0
Join Date: Jun 2011
Posts: 265
Received Thanks: 50
|
Phytagoras ohne math.h
Hey Leute,
Ich hab mich nochmal an meinen "mini Rechner" gesetzt und festgestellt dass unter anderem die Phytagoras-Berechnung fehlt. Wollte das ganze ohne den math.h machen.
Schaut daweil so aus:
PHP Code:
case '5': //Phytagoras c^2 = a^2 * b^2 const double j = 0.00000000001; double i; buffer = ( zahl1 * zahl1 ) * ( zahl2 * zahl2 ); std::cout << "Ergebnis: c^2 = " << buffer << std::endl; for( i = 0.00000000001; i * j != buffer; ) { i = j + i; } erg = i; std::cout << "Ergebnis: c = " << erg << std::endl; break;
Da diese Methode aber zu viel Zeit und Performance in anspruch nimmt, möchte ich fragen ob wer eine andere Idee hat.
Mfg,
Kosic
|
|
|
01/08/2013, 10:09
|
#2
|
elite*gold: 5
Join Date: Sep 2006
Posts: 385
Received Thanks: 218
|
Naja, du könntest inline ASM nutzen und das Zeug somit berechnen.
Code:
int main()
{
auto a = 2 * 2;
auto b = 3 * 3;
auto c = a * b;
double c_root = 0.0f;
__asm
{
fild c;
fsqrt;
fst c_root;
}
}
Ist jedoch ziemlich unflexibel und lässt sich nur mit vergleichbar viel Aufwand erweitern. Abgesehen davon ist das der totale Overkill! Was spricht gegen math.h?
|
|
|
01/08/2013, 10:12
|
#3
|
elite*gold: 0
Join Date: May 2009
Posts: 827
Received Thanks: 471
|
Ich würde vorschlagen, du verwendest das Heron - Verfahren. Ich habe das gerade mal getestet mit 10 Iterationsschritten. Funktioniert sehr schön.
|
|
|
01/08/2013, 15:53
|
#4
|
elite*gold: 7110
Join Date: Jun 2009
Posts: 28,902
Received Thanks: 25,407
|
Ansonsten gibt es für sin, cos, sqrt und Konsorten afaik auch gute Näherungspolynome. Muss es denn so dermaßen exakt sein, dass du in deiner Schleife so kleinschrittig vorgehst? Nicht umsonst rechnen Physiker nicht genauer, als sie messen können
|
|
|
01/08/2013, 21:28
|
#5
|
elite*gold: 0
Join Date: May 2009
Posts: 827
Received Thanks: 471
|
Näherungspolynome sind eher ungeeignet. Man entwickelt hier um einen bestimmten Punkt und erhält dann für genau diesen Punkt genaue Ersatzpolynome. Werte, die weiter weg von diesem Punkt liegen kriegen einen mehr oder weniger großen Fehler mit. Das hängt zum einem vom Grad des Ersatzpolynoms ab zum anderen kommts auch wirklich drauf an, wie weit weg man vom Entwicklungspunkt ist. Iterationsverfahren sind hier weitaus komfortabler.
Bei Sinus (und cos dann auch) verhält sich das nochmal anders. Hier herrscht eine engere Verbindung zur e-Funktion, sprich man kann einen sinus 1:1 in eine Kombination aus e-Funktionen übersetzen. Zum programmieren hilft das allerdings auch nicht wirklich weiter.
Ich werbe an dieser Stelle nochmal für das Heronverfahren ;O
|
|
|
01/08/2013, 23:07
|
#6
|
elite*gold: 0
Join Date: May 2010
Posts: 793
Received Thanks: 268
|
würde dir auch Heronverfahren nahelegen
|
|
|
01/09/2013, 06:24
|
#7
|
elite*gold: 0
Join Date: Jun 2011
Posts: 265
Received Thanks: 50
|
Wenn ichs richtig verstanden habe, müsste es doch so aussehen, oder?( Der erste Näherungsversuch) den Zweiten probiere ich heute Nachmittag.
Code:
buffer = ( zahl1 * zahl1 ) * ( zahl2 * zahl2 );
std::cout << "Ergebnis: c^2 = " << buffer << std::endl;
buffer2 = ( buffer + 1 ) / 2;
buffer3 = buffer / buffer2;
buffer4 = ( buffer2 + buffer3 ) / 2;
erg = buffer4;
std::cout << "Ergebnis: c = " << erg << std::endl;
|
|
|
01/09/2013, 09:42
|
#8
|
elite*gold: 724
Join Date: Mar 2011
Posts: 10,479
Received Thanks: 3,318
|
Machs doch mit Rekursion? Da ist das Heron-Verfahren doch ideal dafür..
x(n + 1) = (x(n) + a / x(n)) / 2 -> x(n) = (x(n - 1) + a / x(n - 1)) / 2
Als Code:
Code:
double x(n, a)
{
double y = (n == 0) ? a : x(n - 1, a);
return (y + a / y) / 2;
}
(das war jetzt nur kurz aus dem Kopf raus, kann man garantiert noch optimieren)
Falls du nicht weißt, wie du das verwenden sollst: erg = x(5, buffer); -> weniger als 5 liefert ein falsches Ergebnis.
Gib Bescheid, ob es klappt.
(bestimmt ist das jetzt komplett falsch und voll peinlich.  )
|
|
|
01/09/2013, 13:50
|
#9
|
elite*gold: 0
Join Date: Jun 2011
Posts: 265
Received Thanks: 50
|
Verstehe deinen Code nicht, snow.
Sorry :S
|
|
|
01/09/2013, 14:06
|
#10
|
elite*gold: 724
Join Date: Mar 2011
Posts: 10,479
Received Thanks: 3,318
|
Ist dir die Rekursion bekannt? Wenn nein, solltest du es evtl. so machen, wie du es bisher gemacht hast.
Code:
double x(n, a)
{
double y = 0;
if (n == 0) // für x(0) kann man a nehmen, statt x(n) + a / x(n) können wir hier also a + a / x einsetzen
y = a;
else
y = x(n - 1, a); // y ist das Ergebnis von x(n -1)
return (y + a / y) / 2; // y in die Formel einsetzen
}
Schwierig zu verstehen, das stimmt. :/
Über eine Iteration ist es evtl. einfacher:
Code:
double wurzel = 0;
for (int i = 0; i < MAX_DURCHLAUF; i++) {
if (i == 0) // wenn es der erste Durchlauf, also x(0) ist
wurzel = (buffer + 1) / 2;
else
wurzel = (wurzel + buffer / wurzel) / 2; // x(nächstes) = (x(aktuelles) + a / x(aktuelles)) / 2
}
printf("Die Wurzel von c beträgt %lf", wurzel);
Keine Ahnung, ob das klappt, hocke hier gerade in der Vorlesung.
|
|
|
01/09/2013, 14:36
|
#11
|
elite*gold: 0
Join Date: Jun 2011
Posts: 265
Received Thanks: 50
|
Habs jetz so gemacht: (Problem solved)
Code:
case '5': //Phytagoras c^2 = a^2 * b^2
float c2;
float x0, x1, x2, x3, x4, x5, x6, x7, x8, x9, x10;
c2 = ( zahl1 * zahl1 ) * ( zahl2 * zahl2 );
std::cout << "Ergebnis: c^2 = " << c2 << std::endl;
x0 = ( c2 + 1 ) / 2;
x1 = ( x0 + ( c2 / x0 ) ) / 2;
x2 = ( x1 + ( c2 / x1 ) ) / 2;
x3 = ( x2 + ( c2 / x2 ) ) / 2;
x4 = ( x3 + ( c2 / x3 ) ) / 2;
x5 = ( x4 + ( c2 / x4 ) ) / 2;
x6 = ( x5 + ( c2 / x5 ) ) / 2;
x7 = ( x6 + ( c2 / x6 ) ) / 2;
x8 = ( x7 + ( c2 / x7 ) ) / 2;
x9 = ( x8 + ( c2 / x8 ) ) / 2;
x10 = ( x9 + ( c2 / x9 ) ) / 2;
erg = x10;
std::cout << "Ergebnis: c = " << erg << std::endl;
break;
|
|
|
01/13/2013, 13:56
|
#12
|
elite*gold: 0
Join Date: Sep 2010
Posts: 10,215
Received Thanks: 5,781
|
Quote:
Originally Posted by xNopex
Näherungspolynome sind eher ungeeignet. Man entwickelt hier um einen bestimmten Punkt und erhält dann für genau diesen Punkt genaue Ersatzpolynome. Werte, die weiter weg von diesem Punkt liegen kriegen einen mehr oder weniger großen Fehler mit. Das hängt zum einem vom Grad des Ersatzpolynoms ab zum anderen kommts auch wirklich drauf an, wie weit weg man vom Entwicklungspunkt ist. Iterationsverfahren sind hier weitaus komfortabler.
Bei Sinus (und cos dann auch) verhält sich das nochmal anders. Hier herrscht eine engere Verbindung zur e-Funktion, sprich man kann einen sinus 1:1 in eine Kombination aus e-Funktionen übersetzen. Zum programmieren hilft das allerdings auch nicht wirklich weiter.
Ich werbe an dieser Stelle nochmal für das Heronverfahren ;O
|
e-Funktion, trigonometrische Funktionen etc. werden vom Taschenrechner und PC alle über Taylor-Reihen berechnet. Die Wurzel kann man dann über diese grundlegenden Funktionen annähern.
sqrt(x) = exp(1/2* ln(x)) = (exp(ln(x)))^(1/2) = sqrt(exp(ln(x))) = sqrt(x)
Zumindest glaube ich, dass das so gehandhabt wird. Nicht, dass ich sonst alle Mathe-Vorlesungen verschlafen würde :-p
|
|
|
01/13/2013, 14:26
|
#13
|
elite*gold: 0
Join Date: May 2009
Posts: 827
Received Thanks: 471
|
Bei Sinus und Co kann ich mir noch vorstellen, dass mit Taylorpolynomen das ganze ausgerechnet wird. Hier genügt es ja eine Periode anzunähern. Werte größer 2pi oder kleiner 0 kann man dann immer auf diese Periode abbilden.
Bei "komplexeren" Funktionen bin ich mir nicht ganz sicher. Die zu verwendenden Taylopolynome müssten hier schon von höherer Ordnung sein, um genaue Ergebnisse zu bekommen. Das Heron-Verfahren wäre im Beispiel der Wurzelfunktion imho einfacher und genauer. Aber ich kenne das Problem mit dem Verschlafen..
|
|
|
01/13/2013, 14:39
|
#14
|
elite*gold: 0
Join Date: Sep 2010
Posts: 10,215
Received Thanks: 5,781
|
Kommt drauf an was du mit komplexeren Funktionen meinst. Im Prinzip ist es doch meistens möglich, eine Funktion durch sin, cos, exp oder log anzunähern. Zu denen kennt man die passenden Reihen-Entwicklungen und somit kann man dann alles in vergleichsweise wenig Iterationsschritten recht genau berechnen.
Wobei mir das Heron-Verfahren eig ganz gut gefällt. Nur gibt es eben nicht immer für jede komplexe Funktion eine so "einfache" Iterationsvorschrift.
|
|
|
01/13/2013, 20:19
|
#15
|
elite*gold: 0
Join Date: May 2009
Posts: 827
Received Thanks: 471
|
Naja im Gegensatz zu sin, cos, etc. die periodisch sind und man deshalb nur eine Periode annähern muss, muss man bei ln, e, etc. über den gesamten Definitionsbereich annähern. Und als Nutzer möchte ich dann natürlich genauso genaue ergebnisse für extrem kleine Werte, wie für extrem große Werte erhalten. Sprich mein Taylorpolynom müsste von höherer Ordnung als die gewohnten ersten zwei Glieder sein, die man so immer mal schriftlich ausrechnet. Ergebnisse auf 9Stellen genau sind meistens genug. Das schafft auch mein Taschenrechner. Jetzt müsste man eben ausrechnen, bis zur welchen Ordnung man entwickeln muss. Mein Gefühl sagt mir, dass das nicht wenig sein wird.
Den Aufwand könnte man sich eben durch z.b. ein Heron Verfahren sparen.
|
|
|
 |
|
Similar Threads
|
[Quest]math.cos und math.sin
08/22/2010 - Metin2 Private Server - 10 Replies
Hallo, anscheinend kennt Metin2 die Funktionen math.cos und math.sin nicht, gibt es trotzdem eine Möglichkeit die irgendwie zu benutzen? (Für den DT ;))
|
iSRO Math
08/03/2009 - Silkroad Online - 30 Replies
Close
|
Math/var help
07/02/2009 - CO2 Private Server - 1 Replies
Ok simplifying this post alot.
How do I transfer things already loaded into the source from a database into the useitem area?
Maybe I'm over complicating things but I am not able to do it..
In my Database.cs I have Struct.SPoints Port = new Struct.SPoints(); loading in things from the database. I need a way to apply those values to a similar code in UseItem.cs where I have my public static void ScrollPointTele(int PointId, int MapEnd, int PointX, int PointY, ClientSocket CSocket)
|
Any good at math
12/11/2006 - Eudemons Online - 3 Replies
Ok I posted a mesage earlier saying im wanting to hack this game. If you want email me for the VB code and i will send you a sample program (not compiled so its 100% virus free) to help you adjust game values. My program will be more usefull however when I find the real address for the character position. Now in replies to my earlier posts some dummy tried saying rotate 45 degrees bla bla bla. I've tried this and still havent got it right. Besides if you notice as you walk around there are no...
|
All times are GMT +1. The time now is 23:00.
|
|