C Newtonverfahren - Nullstellen berechnen

Status
Für weitere Antworten geschlossen.

Int main

Newbie
Registriert
Nov. 2020
Beiträge
3
Hi Community !

Ich hocke seit einiger Zeit an einem Programm zur Berechnung von Nullstellen mittels Newtonverfahren. (Nutzer kann zwischen 5 Funktionen wählen, linke(a) und rechte(b) Grenze, sowie die Genauigkeit(g) festlegen.)

In Sachen C programmieren bin ich eher noch Anfänger.

Zunächst habe ich schon einmal das Problem, dass ich mir über die "fct" Funktion in main weder den Wert f(a) noch f(b) ausgeben kann...es wird immer der Wert -2 ausgegeben ?!?

Des weiteren gehen mir die Ideen aus wie ich unterscheiden kann ob ich den "neuen Mittelwert" von links(a) oder rechts(b) aus berechnen soll. (Vorzeichenunterscheidung)

Kann es sein dass das ganze nicht ohne Zeiger funktioniert ?


Vielen Dank schon mal im Voraus !





C:
#include <stdio.h>

#include <math.h>

#include <stdlib.h>



//f(x) Berechnen

double fct(double x, int fn){
    double fx;

    switch (fn){

        case 1:
            fx = sin(x);
            break;

        case 2:
            fx = exp(x) - 5*x + 1;
            break;

        case 3:
            fx = x*x - 2;
            break;

        case 4:
            fx = 1/7 + 1/x;
            break;

        case 5:
            fx = 2*x - 2;
            break;

        default: printf("Keine Gueltige Option!");

        }

    return fx;

}

      // Nullstelle berechnen

double nullstelle(int fn, double a, double b, double g){

    double xm; //X- An der Stelle des Mittelwerts

    xm = (b - a)/2;

    while ((sqrt(xm*xm) - g ) >= g ){ // muss heißen >= |fx| - g. Wie kommt Wert fx in Funktion nullstelle?

            if (xm < 0){

                xm = (xm - a)/2;

            }

            else xm = (b - xm)/2;

    }

    return xm;

}


int main(void)

{
    int fn;
    double mw;
    double a, b, g;
    double grenzwert;

    while(1){



                    //Vorauswahlen (Funktion/Grenzen/Genauigkeit)

            printf("Waehlen Sie eine Funktion f(x).\n\n");

            printf("1)  sin(x)\n");

            printf("2)  e^x - 5x + 1\n");

            printf("3)  x^2 - 2\n");

            printf("4)  1/7 + 1/x\n");

            printf("5)  2x - 2\n");

            printf("Auswahl: ");

            scanf("%d", &fn);  //Auswahl Funktion


            printf("Linke Grenze: ");

            scanf("%f", &a);     //Linke Grenze



            printf("Rechte Grenze: ");

            scanf("%f", &b);     //Rechte Grenze



            printf("Genauigkeit: ");

            scanf("%f", &g);


            printf("f(x) An Stelle a: %f\n", fct(a, fn));

            printf("f(x) An Stelle b: %f\n", fct(b, fn));

            printf("f(x) am Mittelwert %g\n", nullstelle(fn, a, b, g));


     }

         return 0;
 
Zuletzt bearbeitet:
Nutz mal bitte die passenden Code-Tags. Findest du rechts neben dem Smylie bei den drei Punkten.
 
@PHuV

Ich möchte auch keine Lösung, sondern ich bitte um Tipps.
z.B. ob das ganze überhaupt ohne Zeiger möglich ist.
 
Zuletzt bearbeitet:
Ist das Dein Code oder vorgegebener Code zum Fehler finden?
 
Int main schrieb:
Ich möchte zuerst kurz anmerken, dass das von dir implementierte kein Newton-Verfahren ist, sondern eine Halbierungssuche (binäre Suche) nach der Nullstelle.


Int main schrieb:
Zunächst habe ich schon einmal das Problem, dass ich mir über die "fct" Funktion in main weder den Wert f(a) noch f(b) ausgeben kann...es wird immer der Wert -2 ausgegeben ?!?

Das ist ein fieses C-Problem:
Int main schrieb:
double a;
scanf("%f", &a); //Linke Grenze

Das muss heißen: scanf("%lf", &a). "%f" ist der Format-Specifier für floats. Scanf selbst ist eine vararg-Funktion. Diese Art von Funktionen kennt intern die Typen der Argumente (double * in deinem Fall) nicht mehr. Deshalb muss da zwingend der Format-Specifier mit dem Typ des Arguments übereinstimmen, sonst gibt's undefined behavior.


Int main schrieb:
Des weiteren gehen mir die Ideen aus wie ich unterscheiden kann ob ich den "neuen Mittelwert" von links(a) oder rechts(b) aus berechnen soll. (Vorzeichenunterscheidung)

Du hast ja schon rankommentiert, dass du eingentlich eine Funktionsauswertung brauchst.
Wieso wertest du die Funktion nicht aus, wie du es in der Main auch machst (printf("f(x) An Stelle a: %f\n", fct(a, fn));)?
 
  • Gefällt mir
Reaktionen: Int main
Int main schrieb:
Des weiteren gehen mir die Ideen aus wie ich unterscheiden kann ob ich den "neuen Mittelwert" von links(a) oder rechts(b) aus berechnen soll.
Wir sollten, glaube ich, erst mal klären, ob du jetzt das Intervallhalbierungsverfahren (Bisketion) oder doch das Newtonverfahren implementieren willst.
 
0-8-15 User schrieb:
Wir sollten, glaube ich, erst mal klären, ob du jetzt das Intervallhalbierungsverfahren (Bisketion) oder doch das Newtonverfahren implementieren willst.
Ein bisschen könnte man ihm aber auch übrig lassen bevor man ihm hier jetzt noch das Newton Verfahren programmiert ;).
 
  • Gefällt mir
Reaktionen: PHuV
Status
Für weitere Antworten geschlossen.
Zurück
Oben