C : files manipulation Can't figure out how to simplify this code with files manipulation
I have been working on this code but I can't find out what is wrong. This program does compile and run but it ends up having a fatal error.
The program reads a file and collect the numbers in order to calculate the total (after having converted them to float). Then it reads the file and display the one that has less than 10.00
I have a file called myFile.txt, with the following content :
James------ 07.50 Anthony--- 17.00
So the display should be
- The total is 24.50
- Here is the one with less th开发者_开发技巧an 10.00 :
- James who has 07.50
And here is the code :
int main()
{
int n =2, valueTest=0,count=0;
FILE* file = NULL;
float temp= 00.00f, average= 00.00f, flTen = 10.00f;
float *totalNote = (float*)malloc(n*sizeof(float));
int position = 0;
char selectionNote[5+1], nameBuffer[10+1], noteBuffer[5+1];
file = fopen("c:\\myFile.txt","r");
fseek(file,10,SEEK_SET);
while(valueTest<2)
{
fscanf(file,"%5s",&selectionNote);
temp = atof(selectionNote);
totalNote[position]= temp;
position++;
valeurTest++;
}
for(int counter=0;counter<2;counter++)
{
average += totalNote[counter];
}
printf("The total is : %f \n",average);
rewind(file);
printf("here is the one with less than 10.00 :\n");
while(count<2)
{
fscanf(file,"%10s",&nameBuffer);
fseek(file,10,SEEK_SET);
fscanf(file,"%5s",¬eBuffer);
temp = atof(noteBuffer);
if(temp<flTen)
{
printf("%s who has %f\n",nameBuffer,temp);
}
fseek(file,1,SEEK_SET);
count++;
}
fclose(file);
}
I am pretty new to c and find it more difficult than c# or java. And I woud like to get some suggestions to help me to get better. I think this code could be simplier. Do you think the same ?
You don't mention what platform and compiler you're using. I'm going to guess MSVC and Windows, given that your filename uses a Windows-style path.
You say that the code compiles and runs but have you turned on the warnings from your compiler? That might give you more clues about potentially incorrect things you may be doing.
After fixing some of the typos and adding the standard include headers, I compiled your code in gcc which warned about mismatches between the fscanf
format strings and the arguments. In particular, you are passing a pointer to the char
arrays which is not what you mean. You may want to read up about arrays and pointers in C, e.g. in the C FAQ. The rest of the entries in that document are very enlightening as well.
Most likely, your fatal error is coming from the statement
fscanf(file,"%5s",&selectionNote);
Normally, an expression of array type like selectionNote
will implicitly be converted to a pointer type (see note 1), so in this case the &
is not necessary:
fscanf(file, "%5s", selectionNote);
You don't explain what the code is supposed to be doing, so I'm not exactly sure how to tell you how to restructure it.
- Except when it is the operand of the
sizeof
operator or the unary&
operator, or is a string literal used to initialize an array, an expression that has type ‘‘array of type’’ is converted to an expression with type ‘‘pointer to type’’ that points to the initial element of the array object and is not an lvalue. If the array object has register storage class, the behavior is undefined. -- C Language Standard (draft n1256), section 6.3.2.1, paragraph 3.
Instead of using
fscanf
followed byatof
, use a singlefscanf
with a suitable format string (%f
):fscanf(file, "%f", &totalNote[position]);
You can use the return value from
fscanf
for loop termination, instead of using the variablevalueTest
and the constant2
:while(fscanf(file, "%f", &totalNote[position]) != 0) ...
The first loop that reads from file must scan both the names and the numbers, even though you need only numbers!
You can accumulate the numbers in the same loop that reads them. If you do that, you can remove the array
totalNote
(this "simplification" is not suitable if you think you will extend your code to do other things with the numbers, not just calculate the total)The second loop that reads the file (the one after
rewind
) is better expressed withfor
thanwhile
:for (count = 0; count < counter; count++) ...
In the same loop, you absolutely don't need to use
fseek
! It messes your code up, so it will only read "James" from the file, and never proceed to "Anthony"You probably want to remove the "----" padding from the names before printing them; you can do it with
strchr
orstrtok
:fscanf(file,"%10s",&nameBuffer); strtok(nameBuffer, "-");
精彩评论