2016-11-29 3 views
0

Я пишу следующую программу для моего класса основополагающих принципов программирования (программирование на языке C). Моя IDE дает мне ошибку компиляции для объявления «ученика», как указано в строках, где считывается ввод пользователя. Это также дает мне ошибку относительно стандартов ISO C для вложенных функций в функции letter_grade. Любая помощь будет очень оценена.C Декларация о структуре

#include <stdio.h> 
#include <ctype.h> 
#include <string.h> 

#define MAX 20 

char letter_grade(float a, float b, float c); 

int main(void) 
{ 
char temp_name[MAX]; 
int count=0, last, temp; 

struct student { 
    char f_name[MAX]; 
    char l_name[MAX]; 
    float test1; 
    float test2; 
    float test3; 
    }; 

printf("Please enter the student's last name (Enter ZZZ to exit): "); 
    gets(temp_name); 

while (strncmp(temp_name, "ZZZ\0", 4)) 
{ 
    strncpy(student[count].l_name, temp_name, MAX+1); 
    printf("Please enter the students first name: "); 
    scanf("%s", &student[count].f_name); 
    getchar(); 
    printf("Enter the first test score: "); 
    scanf("%f", &student[count].test1); 
    printf("Enter the second test score: "); 
    scanf("%f", &student[count].test2); 
    printf("Enter the third test score: "); 
    scanf("%f", &student[count].test3); 
    printf("\nPlease enter the student's last name (Enter ZZZ to exit): "); 
    gets(temp_name); 
    count++; 
} 

last = count; 

temp = last + 1; 

printf("\t\t\tStudent Grade Report"); 

for (last;last>=0;last--){ 
    printf("%s, ", student[last].l_name); 
    printf("%s ", student[last].f_name); 
    printf("\t\t Grade: %c\n\n ", letter_grade(student[last].test1, student[last].test2, student[last].test2)); 




// printf("Test Grade: %c\n", letter_grade(85,88,82)); 


return 0; 
} 

char letter_grade(float *a, float *b, float *c) 
{ 
float sum = *a+*b+*c; 

if (sum >= 270.0f) 
    return 'A'; 
if (sum>= 240.0f && sum <270.0f) 
    return 'B'; 
if (sum>= 210.0f && sum <240.0f) 
    return 'C'; 
if (sum>= 180.0f && sum <210.0f) 
    return 'D'; 
if (sum < 180.0f) 
    return 'F'; 
} 
+0

'' l_name' является символ l_name [MAX]; ' но вы указываете 'strncpy' копировать до' MAX + 1'. Просто используйте 'strcpy'. –

+0

настоятельно рекомендуем: последовательно вставить код. отступ после КАЖДОГО открывающего скобки '{'. unindent ПЕРЕД каждой закрывающей скобкой '}'. Предложите, чтобы каждый уровень отступа составлял 4 пробела, достаточно широкий, чтобы быть видимым даже с помощью шрифта переменной ширины. – user3629249

+0

строка символов, как «ZZZ \ 0», автоматически получает байкер терминатора «\ 0», делая массив длиной до 5 символов. ОДНАКО, функция 'strncmp()' перестает сравнивать, когда она встречает '\ 0' в любой строке. – user3629249

ответ

2

Вы нигде не объявлял массив или указатель с именем student. Имя не было объявлено. Таким образом, код, в котором вы ссылаетесь на это имя, как это указано

strncpy(student[count].l_name, temp_name, MAX+1); 
     ^^^^^^^ 

недействителен.

Что такое "студент"? Где это объявлено?

Вы только объявили тип struct student, но это не то же самое, что и объект с именем student.

Кроме того, в этом цикле

for (last;last>=0;last--){ 
    printf("%s, ", student[last].l_name); 
    printf("%s ", student[last].f_name); 
    printf("\t\t Grade: %c\n\n ", letter_grade(student[last].test1, student[last].test2, student[last].test2)); 

там отсутствует закрывающая скобка.

1

Применяя все комментарии и исправление других проблемы в размещенном коде там было много результатов в:

#include <stdio.h> 
#include <string.h> 

#define MAX_NAME_LEN (20) 
#define MAX_STUDENTS (100) 

// define the student struc 
struct student 
{ 
    char f_name[ MAX_NAME_LEN ]; 
    char l_name[ MAX_NAME_LEN ]; 
    float test1; 
    float test2; 
    float test3; 
}; 

char letter_grade(float a, float b, float c); 

int main(void) 
{ 
    // define an array of 100 instances of the student struct 
    struct student students[ MAX_STUDENTS ]; 

    printf("Please enter the student's last name (Enter ZZZ to exit): "); 

    int count=0;  
    while(count < MAX_STUDENTS && scanf(" %19s", students[count].l_name) && strcmp(students[count].l_name, "ZZZ")) 
    { 
     printf("Please enter the students first name: "); 
     scanf(" %19s", students[count].f_name); 

     printf("Enter the first test score: "); 
     scanf("%f", &students[count].test1); 

     printf("Enter the second test score: "); 
     scanf("%f", &students[count].test2); 

     printf("Enter the third test score: "); 
     scanf("%f", &students[count].test3); 

     count++; 

     printf("\nPlease enter the student's last name (Enter ZZZ to exit): "); 
    } // end while 

    printf("\t\t\tStudent Grade Report"); 

    for (; count>=0; count--) 
    { 
     printf("%s, ", students[count].l_name); 
     printf("%s ", students[count].f_name); 
     printf("\t\t Grade: %c\n\n ", 
       letter_grade( students[count].test1, 
           students[count].test2, 
           students[count].test2)); 
    } // end for 
} // end function: main 


char letter_grade(float a, float b, float c) 
{ 
    float sum = a+b+c; 
    char grade; 

    if(sum >= 270.f)  grade = 'A'; 
    else if (sum>= 240.0f) grade = 'B'; 
    else if (sum>= 210.0f) grade = 'C'; 
    else if (sum>= 180.0f) grade = 'D'; 
    else     grade = 'F'; 

    return grade; 
} // end function: letter_grade 

Вы можете сравнить размещенный код в ответ выше, чтобы определить, где были проблемы в посланном код.

Не заполнять заголовочные файлы #include, эти данные не используются.

Переданное значение функции не является указателем в списке параметров вызываемой функции.

В любом if then else последовательности, нет необходимости повторно тест на ранее ликвидированных значения

Опубликованного код вложен одну функции внутри другой, что не правильный код C, хотя может быть разрешен с расширением в gcc компиляторе ,

Там нет необходимости в return заявлении main() если возвращаемое значение равно 0.

На любой не ничтожной функции, ВСЕ пути через код должен привести к return value; заявления.

Проведенный код не смог объявить какой-либо экземпляр структуры struct student. И, конечно же, не объявлял массив этих экземпляров структуры, как это необходимо при обработке нескольких студентов.

Проведенный код (и этот ответ) не удастся, если какое-либо имя или фамилия больше или равно 20 символам.

В этом ответе не проверяются сбои в вызове scanf(), но для надежности такая проверка должна выполняться.Аналогично:

if(1 != scanf(" %19s", students[count].l_name)) 
{ 
    perror("scanf failed"); 
    exit(EXIT_FAILURE); // `exit()` and `EXIT_FAILURE` found in stdlib.h 
} 

// implied else, scanf successful 

while() утверждение в функции main() очень «занят» для ясности, призыв к strcmp() могут быть извлечены и помещены в следующем операторе аналогично:

while(...) 
{ 
    if(!strcmp(students[count].l_name, "ZZZ") { 
    { 
     break; 
    } 
    ... 

В общем , никогда не доверяйте вводам пользователя. Поэтому необходимо проверить возвращаемое значение (не значение параметра) от каждого вызова до scanf().

В качестве упрощения, а не жесткого кодирования длины модификатора MAX в вызовах scanf() с форматом %s спецификатором, можно использовать следующие изменения:

#define MAX_NAME_LEN (19) 
... 
struct student 
{ 
    char f_name[ MAX_NAME_LEN+1 ]; 
    char l_name[ MAX_NAME_LEN+1 ]; 
    float test1; 
    float test2; 
    float test3; 
}; 
.... 
    && scanf(" %" MAX_NAME_LEN "s", students[count].l_name) && 
.... 
    scanf(" %" NAX_NAME_LEN "s", students[count].f_name); 
+0

Примечание: этот параметр для 'printf()' 'letter_grade (students [count] .test1, students [count] .test2, students [count] .test2));' вероятно, должен иметь второй 'учащийся [count] .test2' заменен на: 'students [count] .test3' – user3629249

Смежные вопросы