quadratwurzel näherungsweise bestimmen



  • Hallo,
    hab folgende Aufgabe:
    Erstellen Sie ein C-Programm, das die Quadratwurzel
    y = Wurzel(x)
    näherungsweise zieht. Das Näherungsverfahren arbeitet nach der Vorschrift:
    Yneu = 0,5((x/Yalt)+ Yalt)

    Der Startwert Yalt ist 2/x
    und die Berechnung soll abbrechen, wenn eine
    Genauigkeit von z.B. 8 Stellen nach dem Dezimalpunkt erreicht ist, d.h. die
    Differenz zwischen neu y und alt y soll kleiner als 10^−8 sein.
    Weitere Bemerkungen und Bedingungen:
    • Die Genauigkeitsschranke soll eingegeben werden (also z.B. Eingabe von 8).
    • Im Zyklus sollen jeweils der neue Wert von y und der Absolutwert der
    Differenz ausgegeben werden.
    • Nach dem Zyklus soll das Ergebnis mit 8 Dezimalstellen ausgegeben werden.
    • Zusätzlich soll die Wurzel mit der Standardfunktion sqrt, enthalten in der
    Bibliothek math.h ausgegeben werden.

    Habe bisher folgendes Geschrieben, wobei bei mir allerdings ohne die Anzeige irgendwelcher Fehlermeldungen nur die erste printf anweisung ausgegeben wird.

    #include <stdio.h>
    #include <conio.h>
    #include <math.h>
    
    main()	{
    
    	double Yneu = 0;
    	float Yalt = 0;
    	float x=0;
    	float y2= 0;
    	printf("Von welcher Zahl soll die Wurzel berechnet werden?\n\n");
    	scanf("%f",&x);
    	Yalt= x/2;
    
    while(fabs(Yalt - Yneu)>10e-8f) 
    {	
    
    Yneu = 0.5*((x/Yalt)+Yalt);
    
    }
    printf("y1:%.8f",Yneu);
    
    y2= sqrt(x);
    printf("y2: %.8f", y2);
    	getch();
    }
    

    Würde mich über par Hilfestellungen freuen.
    Schon mal Danke im Voraus.



  • In der Schleife fehlt noch sowas wie Yalt = Yneu , sonst rechnest du immer wieder das gleiche.



  • Hi,

    gegenspammer schrieb:

    Habe bisher folgendes Geschrieben, wobei bei mir allerdings ohne die Anzeige irgendwelcher Fehlermeldungen nur die erste printf anweisung ausgegeben wird.

    Kann ja eigentlich nur eins sein: das Programm steckt in der while Schleife fest.
    Abhilfe: while Bedingung anpassen.



  • Warum ist die Yneu vom Typ double und der Rest vom Typ float? Desweiteren scheint die Genauigkeit von 10^-8 nicht erreicht zu werden, d.h. dein Programm laeuft in einer Endlosschleife.



  • knivil schrieb:

    Warum ist die Yneu vom Typ double und der Rest vom Typ float? Desweiteren scheint die Genauigkeit von 10^-8 nicht erreicht zu werden, d.h. dein Programm laeuft in einer Endlosschleife.

    Habs jetzt mal umgestellt auf alles float,Problem ist halt das sobald ich Genauigkeit auf kleiner 0,1 einstelle sich die Schleife aufhängt.
    Müsste den aber nicht 10^-8 mit float noch darstellbar sein?
    Bzw was müsste ich dann wählen um es darzustelln?

    #include <stdio.h>
    #include <conio.h>
    #include <math.h>
    
    main()	{
    
    	float Yneu = 0;
    	float Yalt = 0;
    	float x=0;
    	float y2= 0;
    	printf("Von welcher Zahl soll die Wurzel berechnet werden?\n\n");
    	scanf("%f",&x);
    	Yalt= x/2;
    
    while(fabs(Yalt - Yneu)>0.001f) 
    {	
    
    Yneu = 0.5*((x/Yalt)+Yalt);
    printf("a");
    
    }
    printf("y1:%.8f",Yneu);
    
    y2= sqrt(x);
    printf("y2: %f", y2);
    	getch();
    }
    


  • Was gefällt dir denn an meiner Antwort nicht?



  • Bashar schrieb:

    Was gefällt dir denn an meiner Antwort nicht?

    naja es steht doch

    Yneu = 0.5*((x/Yalt)+Yalt);
    

    drin.

    Meinste das den net mit Yalt=Yneu?
    Wenn nicht weiß ich net wo und warum man das sdchreiben muss^^

    edit:

    oder meinste das so?

    while(fabs(Yalt - Yneu1)>0.001f) 
    {	
    
    Yneu2 = 0.5*((x/Yalt)+Yalt);
    Yneu1 = Yneu2;
    printf("a");
    
    }
    

    geht aber leider immer noch net

    edit2:
    ich denk mal du willst auf sowas hinaus:

    while(fabs(Yneu - Yalt)>0.001f) 
    {	
    temp = Yneu;
    Yneu = 0.5*((x/Yalt)+Yalt);
    Yalt = temp;
    printf("a");
    
    }
    

    aber irgendwie is das bei mir immer noch falsch -,-



  • Nein, mit Yalt = Yneu meine ich genau das. Sonst hätte ich doch was anderes schreiben können.

    Ja, ich meine ungefähr sowas, wie du unten geschrieben hast, nur nicht so kompliziert.

    Yalt = 0;
    Yneu = x/2;
    while (fabs(Yalt - Yneu)>0.001f) 
    {    
      Yalt = Yneu;
      Yneu = 0.5*((x/Yalt)+Yalt);
    }
    

    Das ganze ist ja eine rekursiv definierte Folge, $$y_{n+1} = \frac{1}{2}(\frac{x}{y_n}+y_n)$$, das heißt aus dem zuletzt berechneten Wert rechnest du den jeweils nächsten aus. Du hast aber den nächsten Wert immer weggeschmissen und im nächsten Durchgang wieder y1 berechnet, ohne je vom Fleck zu kommen.



  • ok vielen dank, habs jetzt endlich verstanden^^

    hätte allerdings noch ne frage,
    ich soll bei der aufgabe ja auch die Genauigkeit einlesen lassen.
    Hatte mir das da jetzt so überlegt:

    main()	{
    
    	float Yneu = 0;
    	float Yalt = 0;
    	float x=0;
    	float y2= 0;
    	float temp = 0;
    	float Genauigkeit= 0;
    	float E = 0;
    	printf("Von welcher Zahl soll die Wurzel berechnet werden?\n\n");
    	scanf("%f",&x);
    	printf("genauigkeit?");
    	scanf("%f",&Genauigkeit);
    	Yneu= x/2;
    	E= -Genauigkeit;
    
    while(fabs(Yneu - Yalt)>10eE)
    {
    Yalt = Yneu;
    Yneu = 0.5*((x/Yalt)+Yalt);
    
    }
    

    Wobei mir dann der compiller als Fehlermeldung ausgibt das ein Exponentwert und nicht meine Variable E erwartet wurde.
    Könnte mir da jmd nen Tip gebn wie man das Problem lösen könnte?



  • Ne, so kannst du nicht Zahlen und Variablen mischen (habe ich zum ersten mal so gesehen, echt lustig -).

    Dazu mußt du die Genauigkeit berechnen lassen, d.h.

    float eps = pow(10.0, -Genauigkeit);
    

    Und die Abfrage dann auf 'eps'...


Anmelden zum Antworten