Copy file into array(structure) using fscanf c












1














I'm trying to write a function that will copy floats from a file using fscanf and put them into an array. I also need to return the number of floats in the file.
Here's what I currently have:



#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
#include <stdlib.h>
#define MAX 100


struct cg {
// structure to hold x and y co-ordinates and mass
float x, y, mass;
}masses[MAX];


int readin(void)
{
FILE *fp;
masses cg;
//Error saying cg is an undeclared identifier.
fp = fopen("m.txt", "rb");
int n = 0;

if (fp == NULL) {
printf("Cannot find file.");
return 0;
}
else {
fscanf(fp, "%f" &cg.x, &cg.y, &cg.mass);
//Error here too
n++;
fclose(fp);
getchar();
return n;

}

}
/* Write this function to read in the data from a file */
/* into the array masses */
/* note that this function should return the number of */
/* masses read in from the file */


void computecg(int n_masses)
{
/* Write this function to compute the C of G */
/* and print the result */
}
void main(void)
{
int number;
if ((number = readin()) > 0) {
computecg(number);
}
}


This is my first year learning c and my lecturer is terrible, and help is much appreciated!










share|improve this question
























  • Note that the declaration at the top is declaring a variable called masses which is an array of struct cgs
    – Alex
    Nov 20 at 1:41










  • either typedef masses or make explicity call use it as "struct cg masses". stackoverflow.com/questions/252780/…
    – Bwebb
    Nov 20 at 1:45










  • In this line: fscanf(fp, "%f" &cg.x, &cg.y, &cg.mass); you are trying to read in three floats, but your format specifier string only has one %f in it. You will need one format specifier for each variable to hold the float. So, you might want it to look like this: fscanf(fp, "%f %f %f" &cg.x, &cg.y, &cg.mass); depending on what your input file looks like.
    – bruceg
    Nov 20 at 1:51










  • Note: the else { after return 0; is unneeded. It's not wrong, just unnecessary. Save yourself the level of indention and just begin with if fscanf(fp, "%f %f %f" &cg.x, &cg.y, &cg.mass) != 3) { /* handle error */ } following the closing } of the if above. Always check the return...
    – David C. Rankin
    Nov 20 at 3:52


















1














I'm trying to write a function that will copy floats from a file using fscanf and put them into an array. I also need to return the number of floats in the file.
Here's what I currently have:



#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
#include <stdlib.h>
#define MAX 100


struct cg {
// structure to hold x and y co-ordinates and mass
float x, y, mass;
}masses[MAX];


int readin(void)
{
FILE *fp;
masses cg;
//Error saying cg is an undeclared identifier.
fp = fopen("m.txt", "rb");
int n = 0;

if (fp == NULL) {
printf("Cannot find file.");
return 0;
}
else {
fscanf(fp, "%f" &cg.x, &cg.y, &cg.mass);
//Error here too
n++;
fclose(fp);
getchar();
return n;

}

}
/* Write this function to read in the data from a file */
/* into the array masses */
/* note that this function should return the number of */
/* masses read in from the file */


void computecg(int n_masses)
{
/* Write this function to compute the C of G */
/* and print the result */
}
void main(void)
{
int number;
if ((number = readin()) > 0) {
computecg(number);
}
}


This is my first year learning c and my lecturer is terrible, and help is much appreciated!










share|improve this question
























  • Note that the declaration at the top is declaring a variable called masses which is an array of struct cgs
    – Alex
    Nov 20 at 1:41










  • either typedef masses or make explicity call use it as "struct cg masses". stackoverflow.com/questions/252780/…
    – Bwebb
    Nov 20 at 1:45










  • In this line: fscanf(fp, "%f" &cg.x, &cg.y, &cg.mass); you are trying to read in three floats, but your format specifier string only has one %f in it. You will need one format specifier for each variable to hold the float. So, you might want it to look like this: fscanf(fp, "%f %f %f" &cg.x, &cg.y, &cg.mass); depending on what your input file looks like.
    – bruceg
    Nov 20 at 1:51










  • Note: the else { after return 0; is unneeded. It's not wrong, just unnecessary. Save yourself the level of indention and just begin with if fscanf(fp, "%f %f %f" &cg.x, &cg.y, &cg.mass) != 3) { /* handle error */ } following the closing } of the if above. Always check the return...
    – David C. Rankin
    Nov 20 at 3:52
















1












1








1







I'm trying to write a function that will copy floats from a file using fscanf and put them into an array. I also need to return the number of floats in the file.
Here's what I currently have:



#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
#include <stdlib.h>
#define MAX 100


struct cg {
// structure to hold x and y co-ordinates and mass
float x, y, mass;
}masses[MAX];


int readin(void)
{
FILE *fp;
masses cg;
//Error saying cg is an undeclared identifier.
fp = fopen("m.txt", "rb");
int n = 0;

if (fp == NULL) {
printf("Cannot find file.");
return 0;
}
else {
fscanf(fp, "%f" &cg.x, &cg.y, &cg.mass);
//Error here too
n++;
fclose(fp);
getchar();
return n;

}

}
/* Write this function to read in the data from a file */
/* into the array masses */
/* note that this function should return the number of */
/* masses read in from the file */


void computecg(int n_masses)
{
/* Write this function to compute the C of G */
/* and print the result */
}
void main(void)
{
int number;
if ((number = readin()) > 0) {
computecg(number);
}
}


This is my first year learning c and my lecturer is terrible, and help is much appreciated!










share|improve this question















I'm trying to write a function that will copy floats from a file using fscanf and put them into an array. I also need to return the number of floats in the file.
Here's what I currently have:



#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
#include <stdlib.h>
#define MAX 100


struct cg {
// structure to hold x and y co-ordinates and mass
float x, y, mass;
}masses[MAX];


int readin(void)
{
FILE *fp;
masses cg;
//Error saying cg is an undeclared identifier.
fp = fopen("m.txt", "rb");
int n = 0;

if (fp == NULL) {
printf("Cannot find file.");
return 0;
}
else {
fscanf(fp, "%f" &cg.x, &cg.y, &cg.mass);
//Error here too
n++;
fclose(fp);
getchar();
return n;

}

}
/* Write this function to read in the data from a file */
/* into the array masses */
/* note that this function should return the number of */
/* masses read in from the file */


void computecg(int n_masses)
{
/* Write this function to compute the C of G */
/* and print the result */
}
void main(void)
{
int number;
if ((number = readin()) > 0) {
computecg(number);
}
}


This is my first year learning c and my lecturer is terrible, and help is much appreciated!







c arrays file structure






share|improve this question















share|improve this question













share|improve this question




share|improve this question








edited Nov 20 at 1:50

























asked Nov 20 at 1:36









ol1ie310

83




83












  • Note that the declaration at the top is declaring a variable called masses which is an array of struct cgs
    – Alex
    Nov 20 at 1:41










  • either typedef masses or make explicity call use it as "struct cg masses". stackoverflow.com/questions/252780/…
    – Bwebb
    Nov 20 at 1:45










  • In this line: fscanf(fp, "%f" &cg.x, &cg.y, &cg.mass); you are trying to read in three floats, but your format specifier string only has one %f in it. You will need one format specifier for each variable to hold the float. So, you might want it to look like this: fscanf(fp, "%f %f %f" &cg.x, &cg.y, &cg.mass); depending on what your input file looks like.
    – bruceg
    Nov 20 at 1:51










  • Note: the else { after return 0; is unneeded. It's not wrong, just unnecessary. Save yourself the level of indention and just begin with if fscanf(fp, "%f %f %f" &cg.x, &cg.y, &cg.mass) != 3) { /* handle error */ } following the closing } of the if above. Always check the return...
    – David C. Rankin
    Nov 20 at 3:52




















  • Note that the declaration at the top is declaring a variable called masses which is an array of struct cgs
    – Alex
    Nov 20 at 1:41










  • either typedef masses or make explicity call use it as "struct cg masses". stackoverflow.com/questions/252780/…
    – Bwebb
    Nov 20 at 1:45










  • In this line: fscanf(fp, "%f" &cg.x, &cg.y, &cg.mass); you are trying to read in three floats, but your format specifier string only has one %f in it. You will need one format specifier for each variable to hold the float. So, you might want it to look like this: fscanf(fp, "%f %f %f" &cg.x, &cg.y, &cg.mass); depending on what your input file looks like.
    – bruceg
    Nov 20 at 1:51










  • Note: the else { after return 0; is unneeded. It's not wrong, just unnecessary. Save yourself the level of indention and just begin with if fscanf(fp, "%f %f %f" &cg.x, &cg.y, &cg.mass) != 3) { /* handle error */ } following the closing } of the if above. Always check the return...
    – David C. Rankin
    Nov 20 at 3:52


















Note that the declaration at the top is declaring a variable called masses which is an array of struct cgs
– Alex
Nov 20 at 1:41




Note that the declaration at the top is declaring a variable called masses which is an array of struct cgs
– Alex
Nov 20 at 1:41












either typedef masses or make explicity call use it as "struct cg masses". stackoverflow.com/questions/252780/…
– Bwebb
Nov 20 at 1:45




either typedef masses or make explicity call use it as "struct cg masses". stackoverflow.com/questions/252780/…
– Bwebb
Nov 20 at 1:45












In this line: fscanf(fp, "%f" &cg.x, &cg.y, &cg.mass); you are trying to read in three floats, but your format specifier string only has one %f in it. You will need one format specifier for each variable to hold the float. So, you might want it to look like this: fscanf(fp, "%f %f %f" &cg.x, &cg.y, &cg.mass); depending on what your input file looks like.
– bruceg
Nov 20 at 1:51




In this line: fscanf(fp, "%f" &cg.x, &cg.y, &cg.mass); you are trying to read in three floats, but your format specifier string only has one %f in it. You will need one format specifier for each variable to hold the float. So, you might want it to look like this: fscanf(fp, "%f %f %f" &cg.x, &cg.y, &cg.mass); depending on what your input file looks like.
– bruceg
Nov 20 at 1:51












Note: the else { after return 0; is unneeded. It's not wrong, just unnecessary. Save yourself the level of indention and just begin with if fscanf(fp, "%f %f %f" &cg.x, &cg.y, &cg.mass) != 3) { /* handle error */ } following the closing } of the if above. Always check the return...
– David C. Rankin
Nov 20 at 3:52






Note: the else { after return 0; is unneeded. It's not wrong, just unnecessary. Save yourself the level of indention and just begin with if fscanf(fp, "%f %f %f" &cg.x, &cg.y, &cg.mass) != 3) { /* handle error */ } following the closing } of the if above. Always check the return...
– David C. Rankin
Nov 20 at 3:52














2 Answers
2






active

oldest

votes


















0














Define your structure cg and declare both the struct cg variables cg and masses as follow: while (n < MAX){ fscanf("%f %f %f", &cg.x, &cg.y, &cg.mass); masses[n] = cg; ++n;} return n;



struct cg {
float x, y, mass;
}cg, masses[MAX];


Then, in the function readin, you should comment the line containing masses cg and in the else block, you can write a while block like the following:



while (n < MAX){
fscanf("%f %f %f", &cg.x, &cg.y, &cg.mass);
masses[n] = cg;
++n;
}
return n;





share|improve this answer





























    0














    There are a number of areas where you can "adjust" things to make your read of the positions and masses a bit more reliable. However, before looking at any of the specifics, let's begin with:



    void main()


    The proper declarations for main are int main (void) and int main (int argc, char **argv) (which you will see written with the equivalent char *argv). note: main is a function of type int and it returns a value. See: C11 Standard §5.1.2.2.1 Program startup p1 (draft n1570). See also: See What should main() return in C and C++?



    Now let's talk about specifics. You define a struct and declare a global array of struct (MAX of them) called masses with:



    struct cg {
    // structure to hold x and y co-ordinates and mass
    float x, y, mass;
    }masses[MAX];


    (note: for any computation, you will want to change float to double to take advantage of the increased precision and to minimize rounding error.)



    While a proper definition and declaration, avoid the use of global variables. They are unnecessary in all but a very few instances. Instead simply declare your struct cg and then declare your array in main() and pass the array as a parameter to each function that needs it. You have a global MAX properly defined, so all you need to pass to the function for filling is the array declared in main() (preferably along with an open file descriptor)



    Why open the file in main() before calling readin()? Obviously, if you attempt to open the file and it fails, there is little need to call readin(). So in general, open the file in the caller, validate the file is open, before passing the open FILE* stream pointer to the function for reading -- otherwise, there is no need to call the function. E.g.



    int main (int argc, char **argv)
    {
    int number;
    struct cg masses[MAX] = {{ .x = 0.0 }};
    /* use filename provided as 1st argument (stdin by default) */
    FILE *fp = argc > 1 ? fopen (argv[1], "r") : stdin;

    if (!fp) { /* validate file open for reading */
    perror ("file open failed");
    return 1;
    }

    if ((number = readin (masses, fp)) > 0) {
    printf ("n%d objects read:nn", number);
    computecg (masses, number);
    }

    if (fp != stdin) fclose (fp); /* close file if not stdin */

    return 0;
    }


    By doing it this way, your readin() reduces to:



    int readin (struct cg *masses, FILE *fp)
    {
    int n = 0;

    while (n < MAX && fscanf (fp, "%lf %lf %lf",
    &masses[n].x, &masses[n].y, &masses[n].mass) == 3)
    n++;

    return n;
    }


    (note: how if (n < MAX && ... in your call to fscanf protects your array bounds by refusing to read more than MAX values. Always protect your array bounds anywhere the possibility exists your code could read more values than you have spaces for...)



    Doing just what it was intended to do readin() the position and mass values from an open file and returning the number of object for which a position and mass was read.



    You simply pass the filled array along with the number of object for which values are stored in your array. For example purposes, simply printing the contents in your masses array in the computecg() function, you could do:



    void computecg (struct cg *masses, int n_masses)
    {
    /* Write this function to compute the C of G */
    /* and print the result */
    for (int i = 0; i < n_masses; i++)
    printf ("%6.2f %6.2f %6.2fn",
    masses[i].x, masses[i].y, masses[i].mass);
    }


    Putting it altogether, the example would be:



    #define _CRT_SECURE_NO_WARNINGS
    #include <stdio.h>
    #include <stdlib.h>

    #define MAX 100

    struct cg { /* define struct, declare instance in main() */
    double x, y, mass; /* (a typedef will make things convenient) */
    };

    int readin (struct cg *masses, FILE *fp)
    {
    int n = 0;

    while (n < MAX && fscanf (fp, "%lf %lf %lf",
    &masses[n].x, &masses[n].y, &masses[n].mass) == 3)
    n++;

    return n;
    }

    void computecg (struct cg *masses, int n_masses)
    {
    /* Write this function to compute the C of G */
    /* and print the result */
    for (int i = 0; i < n_masses; i++)
    printf ("%6.2f %6.2f %6.2fn",
    masses[i].x, masses[i].y, masses[i].mass);
    }

    int main (int argc, char **argv)
    {
    int number;
    struct cg masses[MAX] = {{ .x = 0.0 }};
    /* use filename provided as 1st argument (stdin by default) */
    FILE *fp = argc > 1 ? fopen (argv[1], "r") : stdin;

    if (!fp) { /* validate file open for reading */
    perror ("file open failed");
    return 1;
    }

    if ((number = readin (masses, fp)) > 0) {
    printf ("n%d objects read:nn", number);
    computecg (masses, number);
    }

    if (fp != stdin) fclose (fp); /* close file if not stdin */
    #if defined (_WIN32) || defined (_WIN64)
    getchar();
    #endif
    return 0;
    }


    (note: the #if defined (_WIN32) || defined (_WIN64) is simply used to check if the program is being compiled on windows -- as there is no need to hold the terminal open with a getchar(); otherwise)



    Example Input File



    $ cat dat/cgmasses.txt
    1.37 1.37 713.54
    3.00 3.00 189.55
    1.05 1.05 276.15
    2.57 2.57 238.94
    2.17 2.17 189.03
    6.73 6.73 263.26
    3.26 3.26 795.61
    9.41 9.41 283.92
    1.60 1.60 279.72
    1.70 1.70 719.12


    Example Use/Output



    $ ./bin/cgmasses_read <dat/cgmasses.txt

    10 objects read:

    1.37 1.37 713.54
    3.00 3.00 189.55
    1.05 1.05 276.15
    2.57 2.57 238.94
    2.17 2.17 189.03
    6.73 6.73 263.26
    3.26 3.26 795.61
    9.41 9.41 283.92
    1.60 1.60 279.72
    1.70 1.70 719.12


    The computation of the cg is left to you. Look things over and let me know if you have further questions.






    share|improve this answer





















      Your Answer






      StackExchange.ifUsing("editor", function () {
      StackExchange.using("externalEditor", function () {
      StackExchange.using("snippets", function () {
      StackExchange.snippets.init();
      });
      });
      }, "code-snippets");

      StackExchange.ready(function() {
      var channelOptions = {
      tags: "".split(" "),
      id: "1"
      };
      initTagRenderer("".split(" "), "".split(" "), channelOptions);

      StackExchange.using("externalEditor", function() {
      // Have to fire editor after snippets, if snippets enabled
      if (StackExchange.settings.snippets.snippetsEnabled) {
      StackExchange.using("snippets", function() {
      createEditor();
      });
      }
      else {
      createEditor();
      }
      });

      function createEditor() {
      StackExchange.prepareEditor({
      heartbeatType: 'answer',
      autoActivateHeartbeat: false,
      convertImagesToLinks: true,
      noModals: true,
      showLowRepImageUploadWarning: true,
      reputationToPostImages: 10,
      bindNavPrevention: true,
      postfix: "",
      imageUploader: {
      brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
      contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
      allowUrls: true
      },
      onDemand: true,
      discardSelector: ".discard-answer"
      ,immediatelyShowMarkdownHelp:true
      });


      }
      });














      draft saved

      draft discarded


















      StackExchange.ready(
      function () {
      StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53385020%2fcopy-file-into-arraystructure-using-fscanf-c%23new-answer', 'question_page');
      }
      );

      Post as a guest















      Required, but never shown

























      2 Answers
      2






      active

      oldest

      votes








      2 Answers
      2






      active

      oldest

      votes









      active

      oldest

      votes






      active

      oldest

      votes









      0














      Define your structure cg and declare both the struct cg variables cg and masses as follow: while (n < MAX){ fscanf("%f %f %f", &cg.x, &cg.y, &cg.mass); masses[n] = cg; ++n;} return n;



      struct cg {
      float x, y, mass;
      }cg, masses[MAX];


      Then, in the function readin, you should comment the line containing masses cg and in the else block, you can write a while block like the following:



      while (n < MAX){
      fscanf("%f %f %f", &cg.x, &cg.y, &cg.mass);
      masses[n] = cg;
      ++n;
      }
      return n;





      share|improve this answer


























        0














        Define your structure cg and declare both the struct cg variables cg and masses as follow: while (n < MAX){ fscanf("%f %f %f", &cg.x, &cg.y, &cg.mass); masses[n] = cg; ++n;} return n;



        struct cg {
        float x, y, mass;
        }cg, masses[MAX];


        Then, in the function readin, you should comment the line containing masses cg and in the else block, you can write a while block like the following:



        while (n < MAX){
        fscanf("%f %f %f", &cg.x, &cg.y, &cg.mass);
        masses[n] = cg;
        ++n;
        }
        return n;





        share|improve this answer
























          0












          0








          0






          Define your structure cg and declare both the struct cg variables cg and masses as follow: while (n < MAX){ fscanf("%f %f %f", &cg.x, &cg.y, &cg.mass); masses[n] = cg; ++n;} return n;



          struct cg {
          float x, y, mass;
          }cg, masses[MAX];


          Then, in the function readin, you should comment the line containing masses cg and in the else block, you can write a while block like the following:



          while (n < MAX){
          fscanf("%f %f %f", &cg.x, &cg.y, &cg.mass);
          masses[n] = cg;
          ++n;
          }
          return n;





          share|improve this answer












          Define your structure cg and declare both the struct cg variables cg and masses as follow: while (n < MAX){ fscanf("%f %f %f", &cg.x, &cg.y, &cg.mass); masses[n] = cg; ++n;} return n;



          struct cg {
          float x, y, mass;
          }cg, masses[MAX];


          Then, in the function readin, you should comment the line containing masses cg and in the else block, you can write a while block like the following:



          while (n < MAX){
          fscanf("%f %f %f", &cg.x, &cg.y, &cg.mass);
          masses[n] = cg;
          ++n;
          }
          return n;






          share|improve this answer












          share|improve this answer



          share|improve this answer










          answered Nov 20 at 3:31









          eapetcho

          42927




          42927

























              0














              There are a number of areas where you can "adjust" things to make your read of the positions and masses a bit more reliable. However, before looking at any of the specifics, let's begin with:



              void main()


              The proper declarations for main are int main (void) and int main (int argc, char **argv) (which you will see written with the equivalent char *argv). note: main is a function of type int and it returns a value. See: C11 Standard §5.1.2.2.1 Program startup p1 (draft n1570). See also: See What should main() return in C and C++?



              Now let's talk about specifics. You define a struct and declare a global array of struct (MAX of them) called masses with:



              struct cg {
              // structure to hold x and y co-ordinates and mass
              float x, y, mass;
              }masses[MAX];


              (note: for any computation, you will want to change float to double to take advantage of the increased precision and to minimize rounding error.)



              While a proper definition and declaration, avoid the use of global variables. They are unnecessary in all but a very few instances. Instead simply declare your struct cg and then declare your array in main() and pass the array as a parameter to each function that needs it. You have a global MAX properly defined, so all you need to pass to the function for filling is the array declared in main() (preferably along with an open file descriptor)



              Why open the file in main() before calling readin()? Obviously, if you attempt to open the file and it fails, there is little need to call readin(). So in general, open the file in the caller, validate the file is open, before passing the open FILE* stream pointer to the function for reading -- otherwise, there is no need to call the function. E.g.



              int main (int argc, char **argv)
              {
              int number;
              struct cg masses[MAX] = {{ .x = 0.0 }};
              /* use filename provided as 1st argument (stdin by default) */
              FILE *fp = argc > 1 ? fopen (argv[1], "r") : stdin;

              if (!fp) { /* validate file open for reading */
              perror ("file open failed");
              return 1;
              }

              if ((number = readin (masses, fp)) > 0) {
              printf ("n%d objects read:nn", number);
              computecg (masses, number);
              }

              if (fp != stdin) fclose (fp); /* close file if not stdin */

              return 0;
              }


              By doing it this way, your readin() reduces to:



              int readin (struct cg *masses, FILE *fp)
              {
              int n = 0;

              while (n < MAX && fscanf (fp, "%lf %lf %lf",
              &masses[n].x, &masses[n].y, &masses[n].mass) == 3)
              n++;

              return n;
              }


              (note: how if (n < MAX && ... in your call to fscanf protects your array bounds by refusing to read more than MAX values. Always protect your array bounds anywhere the possibility exists your code could read more values than you have spaces for...)



              Doing just what it was intended to do readin() the position and mass values from an open file and returning the number of object for which a position and mass was read.



              You simply pass the filled array along with the number of object for which values are stored in your array. For example purposes, simply printing the contents in your masses array in the computecg() function, you could do:



              void computecg (struct cg *masses, int n_masses)
              {
              /* Write this function to compute the C of G */
              /* and print the result */
              for (int i = 0; i < n_masses; i++)
              printf ("%6.2f %6.2f %6.2fn",
              masses[i].x, masses[i].y, masses[i].mass);
              }


              Putting it altogether, the example would be:



              #define _CRT_SECURE_NO_WARNINGS
              #include <stdio.h>
              #include <stdlib.h>

              #define MAX 100

              struct cg { /* define struct, declare instance in main() */
              double x, y, mass; /* (a typedef will make things convenient) */
              };

              int readin (struct cg *masses, FILE *fp)
              {
              int n = 0;

              while (n < MAX && fscanf (fp, "%lf %lf %lf",
              &masses[n].x, &masses[n].y, &masses[n].mass) == 3)
              n++;

              return n;
              }

              void computecg (struct cg *masses, int n_masses)
              {
              /* Write this function to compute the C of G */
              /* and print the result */
              for (int i = 0; i < n_masses; i++)
              printf ("%6.2f %6.2f %6.2fn",
              masses[i].x, masses[i].y, masses[i].mass);
              }

              int main (int argc, char **argv)
              {
              int number;
              struct cg masses[MAX] = {{ .x = 0.0 }};
              /* use filename provided as 1st argument (stdin by default) */
              FILE *fp = argc > 1 ? fopen (argv[1], "r") : stdin;

              if (!fp) { /* validate file open for reading */
              perror ("file open failed");
              return 1;
              }

              if ((number = readin (masses, fp)) > 0) {
              printf ("n%d objects read:nn", number);
              computecg (masses, number);
              }

              if (fp != stdin) fclose (fp); /* close file if not stdin */
              #if defined (_WIN32) || defined (_WIN64)
              getchar();
              #endif
              return 0;
              }


              (note: the #if defined (_WIN32) || defined (_WIN64) is simply used to check if the program is being compiled on windows -- as there is no need to hold the terminal open with a getchar(); otherwise)



              Example Input File



              $ cat dat/cgmasses.txt
              1.37 1.37 713.54
              3.00 3.00 189.55
              1.05 1.05 276.15
              2.57 2.57 238.94
              2.17 2.17 189.03
              6.73 6.73 263.26
              3.26 3.26 795.61
              9.41 9.41 283.92
              1.60 1.60 279.72
              1.70 1.70 719.12


              Example Use/Output



              $ ./bin/cgmasses_read <dat/cgmasses.txt

              10 objects read:

              1.37 1.37 713.54
              3.00 3.00 189.55
              1.05 1.05 276.15
              2.57 2.57 238.94
              2.17 2.17 189.03
              6.73 6.73 263.26
              3.26 3.26 795.61
              9.41 9.41 283.92
              1.60 1.60 279.72
              1.70 1.70 719.12


              The computation of the cg is left to you. Look things over and let me know if you have further questions.






              share|improve this answer


























                0














                There are a number of areas where you can "adjust" things to make your read of the positions and masses a bit more reliable. However, before looking at any of the specifics, let's begin with:



                void main()


                The proper declarations for main are int main (void) and int main (int argc, char **argv) (which you will see written with the equivalent char *argv). note: main is a function of type int and it returns a value. See: C11 Standard §5.1.2.2.1 Program startup p1 (draft n1570). See also: See What should main() return in C and C++?



                Now let's talk about specifics. You define a struct and declare a global array of struct (MAX of them) called masses with:



                struct cg {
                // structure to hold x and y co-ordinates and mass
                float x, y, mass;
                }masses[MAX];


                (note: for any computation, you will want to change float to double to take advantage of the increased precision and to minimize rounding error.)



                While a proper definition and declaration, avoid the use of global variables. They are unnecessary in all but a very few instances. Instead simply declare your struct cg and then declare your array in main() and pass the array as a parameter to each function that needs it. You have a global MAX properly defined, so all you need to pass to the function for filling is the array declared in main() (preferably along with an open file descriptor)



                Why open the file in main() before calling readin()? Obviously, if you attempt to open the file and it fails, there is little need to call readin(). So in general, open the file in the caller, validate the file is open, before passing the open FILE* stream pointer to the function for reading -- otherwise, there is no need to call the function. E.g.



                int main (int argc, char **argv)
                {
                int number;
                struct cg masses[MAX] = {{ .x = 0.0 }};
                /* use filename provided as 1st argument (stdin by default) */
                FILE *fp = argc > 1 ? fopen (argv[1], "r") : stdin;

                if (!fp) { /* validate file open for reading */
                perror ("file open failed");
                return 1;
                }

                if ((number = readin (masses, fp)) > 0) {
                printf ("n%d objects read:nn", number);
                computecg (masses, number);
                }

                if (fp != stdin) fclose (fp); /* close file if not stdin */

                return 0;
                }


                By doing it this way, your readin() reduces to:



                int readin (struct cg *masses, FILE *fp)
                {
                int n = 0;

                while (n < MAX && fscanf (fp, "%lf %lf %lf",
                &masses[n].x, &masses[n].y, &masses[n].mass) == 3)
                n++;

                return n;
                }


                (note: how if (n < MAX && ... in your call to fscanf protects your array bounds by refusing to read more than MAX values. Always protect your array bounds anywhere the possibility exists your code could read more values than you have spaces for...)



                Doing just what it was intended to do readin() the position and mass values from an open file and returning the number of object for which a position and mass was read.



                You simply pass the filled array along with the number of object for which values are stored in your array. For example purposes, simply printing the contents in your masses array in the computecg() function, you could do:



                void computecg (struct cg *masses, int n_masses)
                {
                /* Write this function to compute the C of G */
                /* and print the result */
                for (int i = 0; i < n_masses; i++)
                printf ("%6.2f %6.2f %6.2fn",
                masses[i].x, masses[i].y, masses[i].mass);
                }


                Putting it altogether, the example would be:



                #define _CRT_SECURE_NO_WARNINGS
                #include <stdio.h>
                #include <stdlib.h>

                #define MAX 100

                struct cg { /* define struct, declare instance in main() */
                double x, y, mass; /* (a typedef will make things convenient) */
                };

                int readin (struct cg *masses, FILE *fp)
                {
                int n = 0;

                while (n < MAX && fscanf (fp, "%lf %lf %lf",
                &masses[n].x, &masses[n].y, &masses[n].mass) == 3)
                n++;

                return n;
                }

                void computecg (struct cg *masses, int n_masses)
                {
                /* Write this function to compute the C of G */
                /* and print the result */
                for (int i = 0; i < n_masses; i++)
                printf ("%6.2f %6.2f %6.2fn",
                masses[i].x, masses[i].y, masses[i].mass);
                }

                int main (int argc, char **argv)
                {
                int number;
                struct cg masses[MAX] = {{ .x = 0.0 }};
                /* use filename provided as 1st argument (stdin by default) */
                FILE *fp = argc > 1 ? fopen (argv[1], "r") : stdin;

                if (!fp) { /* validate file open for reading */
                perror ("file open failed");
                return 1;
                }

                if ((number = readin (masses, fp)) > 0) {
                printf ("n%d objects read:nn", number);
                computecg (masses, number);
                }

                if (fp != stdin) fclose (fp); /* close file if not stdin */
                #if defined (_WIN32) || defined (_WIN64)
                getchar();
                #endif
                return 0;
                }


                (note: the #if defined (_WIN32) || defined (_WIN64) is simply used to check if the program is being compiled on windows -- as there is no need to hold the terminal open with a getchar(); otherwise)



                Example Input File



                $ cat dat/cgmasses.txt
                1.37 1.37 713.54
                3.00 3.00 189.55
                1.05 1.05 276.15
                2.57 2.57 238.94
                2.17 2.17 189.03
                6.73 6.73 263.26
                3.26 3.26 795.61
                9.41 9.41 283.92
                1.60 1.60 279.72
                1.70 1.70 719.12


                Example Use/Output



                $ ./bin/cgmasses_read <dat/cgmasses.txt

                10 objects read:

                1.37 1.37 713.54
                3.00 3.00 189.55
                1.05 1.05 276.15
                2.57 2.57 238.94
                2.17 2.17 189.03
                6.73 6.73 263.26
                3.26 3.26 795.61
                9.41 9.41 283.92
                1.60 1.60 279.72
                1.70 1.70 719.12


                The computation of the cg is left to you. Look things over and let me know if you have further questions.






                share|improve this answer
























                  0












                  0








                  0






                  There are a number of areas where you can "adjust" things to make your read of the positions and masses a bit more reliable. However, before looking at any of the specifics, let's begin with:



                  void main()


                  The proper declarations for main are int main (void) and int main (int argc, char **argv) (which you will see written with the equivalent char *argv). note: main is a function of type int and it returns a value. See: C11 Standard §5.1.2.2.1 Program startup p1 (draft n1570). See also: See What should main() return in C and C++?



                  Now let's talk about specifics. You define a struct and declare a global array of struct (MAX of them) called masses with:



                  struct cg {
                  // structure to hold x and y co-ordinates and mass
                  float x, y, mass;
                  }masses[MAX];


                  (note: for any computation, you will want to change float to double to take advantage of the increased precision and to minimize rounding error.)



                  While a proper definition and declaration, avoid the use of global variables. They are unnecessary in all but a very few instances. Instead simply declare your struct cg and then declare your array in main() and pass the array as a parameter to each function that needs it. You have a global MAX properly defined, so all you need to pass to the function for filling is the array declared in main() (preferably along with an open file descriptor)



                  Why open the file in main() before calling readin()? Obviously, if you attempt to open the file and it fails, there is little need to call readin(). So in general, open the file in the caller, validate the file is open, before passing the open FILE* stream pointer to the function for reading -- otherwise, there is no need to call the function. E.g.



                  int main (int argc, char **argv)
                  {
                  int number;
                  struct cg masses[MAX] = {{ .x = 0.0 }};
                  /* use filename provided as 1st argument (stdin by default) */
                  FILE *fp = argc > 1 ? fopen (argv[1], "r") : stdin;

                  if (!fp) { /* validate file open for reading */
                  perror ("file open failed");
                  return 1;
                  }

                  if ((number = readin (masses, fp)) > 0) {
                  printf ("n%d objects read:nn", number);
                  computecg (masses, number);
                  }

                  if (fp != stdin) fclose (fp); /* close file if not stdin */

                  return 0;
                  }


                  By doing it this way, your readin() reduces to:



                  int readin (struct cg *masses, FILE *fp)
                  {
                  int n = 0;

                  while (n < MAX && fscanf (fp, "%lf %lf %lf",
                  &masses[n].x, &masses[n].y, &masses[n].mass) == 3)
                  n++;

                  return n;
                  }


                  (note: how if (n < MAX && ... in your call to fscanf protects your array bounds by refusing to read more than MAX values. Always protect your array bounds anywhere the possibility exists your code could read more values than you have spaces for...)



                  Doing just what it was intended to do readin() the position and mass values from an open file and returning the number of object for which a position and mass was read.



                  You simply pass the filled array along with the number of object for which values are stored in your array. For example purposes, simply printing the contents in your masses array in the computecg() function, you could do:



                  void computecg (struct cg *masses, int n_masses)
                  {
                  /* Write this function to compute the C of G */
                  /* and print the result */
                  for (int i = 0; i < n_masses; i++)
                  printf ("%6.2f %6.2f %6.2fn",
                  masses[i].x, masses[i].y, masses[i].mass);
                  }


                  Putting it altogether, the example would be:



                  #define _CRT_SECURE_NO_WARNINGS
                  #include <stdio.h>
                  #include <stdlib.h>

                  #define MAX 100

                  struct cg { /* define struct, declare instance in main() */
                  double x, y, mass; /* (a typedef will make things convenient) */
                  };

                  int readin (struct cg *masses, FILE *fp)
                  {
                  int n = 0;

                  while (n < MAX && fscanf (fp, "%lf %lf %lf",
                  &masses[n].x, &masses[n].y, &masses[n].mass) == 3)
                  n++;

                  return n;
                  }

                  void computecg (struct cg *masses, int n_masses)
                  {
                  /* Write this function to compute the C of G */
                  /* and print the result */
                  for (int i = 0; i < n_masses; i++)
                  printf ("%6.2f %6.2f %6.2fn",
                  masses[i].x, masses[i].y, masses[i].mass);
                  }

                  int main (int argc, char **argv)
                  {
                  int number;
                  struct cg masses[MAX] = {{ .x = 0.0 }};
                  /* use filename provided as 1st argument (stdin by default) */
                  FILE *fp = argc > 1 ? fopen (argv[1], "r") : stdin;

                  if (!fp) { /* validate file open for reading */
                  perror ("file open failed");
                  return 1;
                  }

                  if ((number = readin (masses, fp)) > 0) {
                  printf ("n%d objects read:nn", number);
                  computecg (masses, number);
                  }

                  if (fp != stdin) fclose (fp); /* close file if not stdin */
                  #if defined (_WIN32) || defined (_WIN64)
                  getchar();
                  #endif
                  return 0;
                  }


                  (note: the #if defined (_WIN32) || defined (_WIN64) is simply used to check if the program is being compiled on windows -- as there is no need to hold the terminal open with a getchar(); otherwise)



                  Example Input File



                  $ cat dat/cgmasses.txt
                  1.37 1.37 713.54
                  3.00 3.00 189.55
                  1.05 1.05 276.15
                  2.57 2.57 238.94
                  2.17 2.17 189.03
                  6.73 6.73 263.26
                  3.26 3.26 795.61
                  9.41 9.41 283.92
                  1.60 1.60 279.72
                  1.70 1.70 719.12


                  Example Use/Output



                  $ ./bin/cgmasses_read <dat/cgmasses.txt

                  10 objects read:

                  1.37 1.37 713.54
                  3.00 3.00 189.55
                  1.05 1.05 276.15
                  2.57 2.57 238.94
                  2.17 2.17 189.03
                  6.73 6.73 263.26
                  3.26 3.26 795.61
                  9.41 9.41 283.92
                  1.60 1.60 279.72
                  1.70 1.70 719.12


                  The computation of the cg is left to you. Look things over and let me know if you have further questions.






                  share|improve this answer












                  There are a number of areas where you can "adjust" things to make your read of the positions and masses a bit more reliable. However, before looking at any of the specifics, let's begin with:



                  void main()


                  The proper declarations for main are int main (void) and int main (int argc, char **argv) (which you will see written with the equivalent char *argv). note: main is a function of type int and it returns a value. See: C11 Standard §5.1.2.2.1 Program startup p1 (draft n1570). See also: See What should main() return in C and C++?



                  Now let's talk about specifics. You define a struct and declare a global array of struct (MAX of them) called masses with:



                  struct cg {
                  // structure to hold x and y co-ordinates and mass
                  float x, y, mass;
                  }masses[MAX];


                  (note: for any computation, you will want to change float to double to take advantage of the increased precision and to minimize rounding error.)



                  While a proper definition and declaration, avoid the use of global variables. They are unnecessary in all but a very few instances. Instead simply declare your struct cg and then declare your array in main() and pass the array as a parameter to each function that needs it. You have a global MAX properly defined, so all you need to pass to the function for filling is the array declared in main() (preferably along with an open file descriptor)



                  Why open the file in main() before calling readin()? Obviously, if you attempt to open the file and it fails, there is little need to call readin(). So in general, open the file in the caller, validate the file is open, before passing the open FILE* stream pointer to the function for reading -- otherwise, there is no need to call the function. E.g.



                  int main (int argc, char **argv)
                  {
                  int number;
                  struct cg masses[MAX] = {{ .x = 0.0 }};
                  /* use filename provided as 1st argument (stdin by default) */
                  FILE *fp = argc > 1 ? fopen (argv[1], "r") : stdin;

                  if (!fp) { /* validate file open for reading */
                  perror ("file open failed");
                  return 1;
                  }

                  if ((number = readin (masses, fp)) > 0) {
                  printf ("n%d objects read:nn", number);
                  computecg (masses, number);
                  }

                  if (fp != stdin) fclose (fp); /* close file if not stdin */

                  return 0;
                  }


                  By doing it this way, your readin() reduces to:



                  int readin (struct cg *masses, FILE *fp)
                  {
                  int n = 0;

                  while (n < MAX && fscanf (fp, "%lf %lf %lf",
                  &masses[n].x, &masses[n].y, &masses[n].mass) == 3)
                  n++;

                  return n;
                  }


                  (note: how if (n < MAX && ... in your call to fscanf protects your array bounds by refusing to read more than MAX values. Always protect your array bounds anywhere the possibility exists your code could read more values than you have spaces for...)



                  Doing just what it was intended to do readin() the position and mass values from an open file and returning the number of object for which a position and mass was read.



                  You simply pass the filled array along with the number of object for which values are stored in your array. For example purposes, simply printing the contents in your masses array in the computecg() function, you could do:



                  void computecg (struct cg *masses, int n_masses)
                  {
                  /* Write this function to compute the C of G */
                  /* and print the result */
                  for (int i = 0; i < n_masses; i++)
                  printf ("%6.2f %6.2f %6.2fn",
                  masses[i].x, masses[i].y, masses[i].mass);
                  }


                  Putting it altogether, the example would be:



                  #define _CRT_SECURE_NO_WARNINGS
                  #include <stdio.h>
                  #include <stdlib.h>

                  #define MAX 100

                  struct cg { /* define struct, declare instance in main() */
                  double x, y, mass; /* (a typedef will make things convenient) */
                  };

                  int readin (struct cg *masses, FILE *fp)
                  {
                  int n = 0;

                  while (n < MAX && fscanf (fp, "%lf %lf %lf",
                  &masses[n].x, &masses[n].y, &masses[n].mass) == 3)
                  n++;

                  return n;
                  }

                  void computecg (struct cg *masses, int n_masses)
                  {
                  /* Write this function to compute the C of G */
                  /* and print the result */
                  for (int i = 0; i < n_masses; i++)
                  printf ("%6.2f %6.2f %6.2fn",
                  masses[i].x, masses[i].y, masses[i].mass);
                  }

                  int main (int argc, char **argv)
                  {
                  int number;
                  struct cg masses[MAX] = {{ .x = 0.0 }};
                  /* use filename provided as 1st argument (stdin by default) */
                  FILE *fp = argc > 1 ? fopen (argv[1], "r") : stdin;

                  if (!fp) { /* validate file open for reading */
                  perror ("file open failed");
                  return 1;
                  }

                  if ((number = readin (masses, fp)) > 0) {
                  printf ("n%d objects read:nn", number);
                  computecg (masses, number);
                  }

                  if (fp != stdin) fclose (fp); /* close file if not stdin */
                  #if defined (_WIN32) || defined (_WIN64)
                  getchar();
                  #endif
                  return 0;
                  }


                  (note: the #if defined (_WIN32) || defined (_WIN64) is simply used to check if the program is being compiled on windows -- as there is no need to hold the terminal open with a getchar(); otherwise)



                  Example Input File



                  $ cat dat/cgmasses.txt
                  1.37 1.37 713.54
                  3.00 3.00 189.55
                  1.05 1.05 276.15
                  2.57 2.57 238.94
                  2.17 2.17 189.03
                  6.73 6.73 263.26
                  3.26 3.26 795.61
                  9.41 9.41 283.92
                  1.60 1.60 279.72
                  1.70 1.70 719.12


                  Example Use/Output



                  $ ./bin/cgmasses_read <dat/cgmasses.txt

                  10 objects read:

                  1.37 1.37 713.54
                  3.00 3.00 189.55
                  1.05 1.05 276.15
                  2.57 2.57 238.94
                  2.17 2.17 189.03
                  6.73 6.73 263.26
                  3.26 3.26 795.61
                  9.41 9.41 283.92
                  1.60 1.60 279.72
                  1.70 1.70 719.12


                  The computation of the cg is left to you. Look things over and let me know if you have further questions.







                  share|improve this answer












                  share|improve this answer



                  share|improve this answer










                  answered Nov 20 at 4:48









                  David C. Rankin

                  40.1k32647




                  40.1k32647






























                      draft saved

                      draft discarded




















































                      Thanks for contributing an answer to Stack Overflow!


                      • Please be sure to answer the question. Provide details and share your research!

                      But avoid



                      • Asking for help, clarification, or responding to other answers.

                      • Making statements based on opinion; back them up with references or personal experience.


                      To learn more, see our tips on writing great answers.





                      Some of your past answers have not been well-received, and you're in danger of being blocked from answering.


                      Please pay close attention to the following guidance:


                      • Please be sure to answer the question. Provide details and share your research!

                      But avoid



                      • Asking for help, clarification, or responding to other answers.

                      • Making statements based on opinion; back them up with references or personal experience.


                      To learn more, see our tips on writing great answers.




                      draft saved


                      draft discarded














                      StackExchange.ready(
                      function () {
                      StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53385020%2fcopy-file-into-arraystructure-using-fscanf-c%23new-answer', 'question_page');
                      }
                      );

                      Post as a guest















                      Required, but never shown





















































                      Required, but never shown














                      Required, but never shown












                      Required, but never shown







                      Required, but never shown

































                      Required, but never shown














                      Required, but never shown












                      Required, but never shown







                      Required, but never shown







                      Popular posts from this blog

                      If I really need a card on my start hand, how many mulligans make sense? [duplicate]

                      Alcedinidae

                      Can an atomic nucleus contain both particles and antiparticles? [duplicate]