Flächeninhalt eines n-Ecks durch Koordinaten berechnen



  • @lfahs sagte in Flächeninhalt eines n-Ecks durch Koordinaten berechnen:

    @Swordfish *(-1) habe ich gerechnet, damit ich den Betrag bekomme

    Für den Betrag kannst du die Funktion fabs benutzen.

    Generell solltest du unbedingt Einlesen und Berechnen in zwei Funktionen auslagern. Dann kannst du dir auch leicht ein paar Beispiel-n-Ecks fest kodieren und alle auf einmal mit deiner Funktion testen.

    Du kannst auch einen "echten" Punkt mit x und y machen anstatt ein weiteres 2-elementiges Array zu nehmen, z.B. so:

    typedef struct { 
        double x; 
        double y;
    } point_t;
    


  • @lfahs sagte in Flächeninhalt eines n-Ecks durch Koordinaten berechnen:

    @Swordfish okay dann ändere ich das in float.

    ich hoffe Du hast den Punkt hinter der 2 in

    @Swordfish sagte in Flächeninhalt eines n-Ecks durch Koordinaten berechnen:

    3 / 2. = 1.5

    bemerkt.

    2. (oder auch 2.0) ist ein double literal
    2f (oder auch 2.0f) ist ein float literal



  • @Swordfish alles klar. So ganz funktioniert das Programm momentan noch nicht. Für manche Beispiele bekomme ich das richtige Ergebnis und für andere nicht



  • @lfahs sagte in Flächeninhalt eines n-Ecks durch Koordinaten berechnen:

    So ganz funktioniert das Programm momentan noch nicht. Für manche Beispiele bekomme ich das richtige Ergebnis und für andere nicht

    Was sind eigentlich GF, TF und RF? Ein paar mehr Buchstaben tun gut, damit man die Variablen gleich versteht. Nimm Abstand von diesen stark abgekürzten Variablennamen! (Ausnahme: int i für Zähler sowie x und y für gleichnamige Koordinaten sind ok - und ggf. weitere Konventionen oder fachlich übliche Abkürzungen).

    Du hattest oben auch noch irgendwo ein "abs". Ist daraus auch ein fabs geworden? Wie sieht dein Code jetzt aus?



  • @wob

    #include <stdio.h>
    #include <stdlib.h>
    #include <math.h>
    
    int main(void) {
        
        int n;
        
        double GF = 0; // Gesamtfläche
        double TF = 0; // Teilfläche
        double RF = 0; // Restfläche
        
        printf("\n Geben Sie die Anzahl der Ecken ein: ");
        scanf("%d",&n);
        
    
        float P[n][2];
        
        for(int i=0;i<n;i++){          // Koordinaten einlesen
            for(int j=0;j<2;j++){
                
                printf(" P_%d,%d =",i,j);
                scanf("%f",&(P[i][j]));
            }
        }
        
        for(int i=0;i<n;i++){        // Teilflächen berechnen
    
                TF += (P[i][1]*P[i+1][0]) - (P[i][0]*P[i+1][1]);
    
            }
    
        
        RF = (P[0][0]*P[n-1][1])-(P[n-1][0]*P[0][1]);
        
        GF = TF + RF;
        
        printf(" Fläche: %f \n", fabs (GF) /2);
            
        return 0;
        
    }
    

    für das Beispiel: P1(1/-1), P2(0/1), P3(-1/-1) funktioniert es

    für: P1(1/-1),P2(2/1),P3(-1/1),P4(-2/-2) hingegen nicht



  • @lfahs sagte in Flächeninhalt eines n-Ecks durch Koordinaten berechnen:

    P[i+1][0]

    Das läuft immer noch zu weit.



  • This post is deleted!


  • @manni66 ah danke, hab es jetzt endlich richtig und auch verstanden



  • Wie gesagt, nimm dir zu Herzen, den Code in Funktionen zu teilen, z.B. so:

    #include <stdio.h>
    #include <stdlib.h>
    #include <math.h>
    
    typedef struct {
        double x;
        double y;
    } point_t;
    
    
    double area(point_t P[], size_t n)
    {
        double GF = 0; // Gesamtfläche
        double TF = 0; // Teilfläche
        double RF = 0; // Restfläche
    
        // Teilflächen berechnen
        for (size_t i = 0; i < n - 1; i++) {
            TF += (P[i].y * P[i + 1].x) - (P[i].x * P[i + 1].y);
        }
    
        RF = (P[0].x * P[n - 1].y) - (P[n - 1].x * P[0].y);
        GF = TF + RF;
        return GF / 2;
    }
    
    
    int main(void)
    {
        point_t quadrat[4] = {
            {.x = 0, .y = 0},
            {.x = 0, .y = 1},
            {.x = 1, .y = 1},
            {.x = 1, .y = 0}
        };
        point_t quadratVerschoben[4] = {
            {.x = 0.4, .y = 0.7},
            {.x = 0.4, .y = 1.7},
            {.x = 1.4, .y = 1.7},
            {.x = 1.4, .y = 0.7}
        };
        point_t dreieck[3] = {
            {.x = -0.5, .y = 0.},
            {.x = 0.5, .y = 0.},
            {.x = 0, .y = 1}
        };
    
        printf(" Fläche Quadrat: %f \n", area(quadrat, 4));
        printf(" Fläche Quadrat (verschoben): %f \n", area(quadratVerschoben, 4));
        printf(" Fläche Dreieck: %f \n", area(dreieck, 3));
    
        return 0;
    }
    

    Analog zu meinen Tests könntest du dann einfach eine Eingabefunktion schreiben. Aber so brauchst du nicht jedes Mal beim Ausprobieren deines Codes neu Zahlen einzugeben. Aber mir scheint das so nicht korrekt, wenn ich auf die Fläche des Dreiecks gucke... Du solltest vielleicht auch noch ein andere, größere n-Ecken testen.



  • #include <stddef.h>
    #include <stdbool.h>
    #include <stdlib.h>
    #include <stdio.h>
    
    typedef struct point_tag {
        double x;
        double y;
    } point_t;
    
    bool read_point(FILE *stream, point_t *point)
    {
        point_t tmp;
        if (fscanf(stream, "%lf %lf", &tmp.x, &tmp.y) != 2)
            return false;
        *point = tmp;
        return true;
    }
    
    void print_point(FILE *stream, point_t const *point)
    {
        fprintf(stream, "(%lf, %lf)", point->x, point->y);
    }
    
    void print_points(FILE *stream, point_t const *points, size_t num_points)
    {
        for (size_t i = 0; i < num_points; ++i) {
            fprint_point(stream, &points[i]);
            putchar('\n');
        }
    }
    
    size_t read_points(FILE *stream, point_t **points)
    {
        size_t num_points = 0;
        *points = NULL;
        for (point_t tmp = { 0 }; fread_point(stream, &tmp);) {
            point_t *new_points = realloc(*points, sizeof * new_points * (num_points + 1));
            if (!new_points) {
                free(*points);
                return 0;
            }
            new_points[num_points++] = tmp;
            *points = new_points;        
        }
        return num_points;
    }
    
    double area(point_t *points, size_t num_points)
    {
        double area = 0.;
        for (size_t i = 0; i < num_points - 1; ++i)
            area += (points[i].x + points[i + 1].x) * (points[i].y - points[i + 1].y);
        return area / 2.;
    }
    
    int main()
    {
        point_t *points;
        size_t num_points = read_points(stdin, &points);
        print_points(stdout, points, num_points);
        printf("Area: %f", area(points, num_points));
        free(points);
    }
    

    Aber bitte beachten daß das nur für sich nicht selbst schneidende Polygone funktioniert. Sonst siehe Bentley–Ottmann algorithm.


Log in to reply