error: expected expression before 'student' - c

very new to c. I wrote the following code.
typedef struct
{
char name[100];
int comp, math, phys;
int total;
} student[100];
int main(int argc, char** argv) {
int number;
do
{
printf("Enter how many students: ");
scanf("%d", &number);
if(number < 0)
{
printf("Wrong input! \n");
}
}
while(number < 0);
int i;
for(i=0; i < number; ++i)
{
printf("Student %d's name: ", i+1);
scanf("%s", student[i].name);
printf("Comp: " );
scanf("%d", &student[i].comp);
printf("Phys: " );
scanf("%d", &student[i].phys);
printf("Math: " );
scanf("%d", &student[i].math);
&student[i].total = &student[i].comp + &student[i].math + &student[i].phys;
}
printf("s%", &student[1].name);
return (EXIT_SUCCESS);
}
I keep getting error: expected expression before 'student' in all the scanf lines and the last printf line. What am I doing wrong? Very new to C so any help would be great.

Do
struct
{
char name[100];
int comp, math, phys;
int total;
} student[100];
If you want to combine the definition and identifier. You should know that student isn't a type, it's an array of structs without a name. There are alternatives to what you want to accomplish. For example:
typedef struct student
{
char name[100];
int comp, math, phys;
int total;
} student;
student students[100];

Drop the typedef keyword. You're wanting to create an array of 100 student objects, not a type name representing an array of 100 students.
Hopefully this helps you in the future:
// `Type var` is a shorter way to write `struct tag var`
// `Type` is just an alias (another name) for `struct tag`
typedef struct tag {
int x;
} Type;
// `Type100 arr` is a shorter way to write `struct tag100 arr[100]`
// `Type100` is just an alias for `struct tag100[100]`
// No, you can't do `struct tag100[100] arr`; `Type100 arr` gets around this restriction
typedef struct tag100 {
int x;
} Type100[100];
// `var` contains a single value of type `struct tagX`
struct tagX {
int x;
} var;
// `arr` is an array of 100 values of type `struct tagX100`
struct tagX100 {
int x;
} arr[100];

Related

Structure function pointer parameter?

Fields of Student:​ name, lastName, studentId, mid1Grade, mid2Grade, finalGrade, average
Fields of Course:​ courseName, courseCode, myStudentArray (array of Student structures),currentStudentCount
Functions:
void createNewStudent(struct Course *myCourse);
void setGradeOfStudent(struct Course *myCourse);
void findAndDisplayAverage(struct Course *myCourse);
struct Student * findStudentByID(int id, struct Course *myCourse);
void displayAverageOfAllStudents(struct Course *myCourse);
void displayAverageOfStudentsInInterval(struct Course *myCourse
ok so I have written the first function but there is an error which I dont understand. First of all the first function and what it does:
createNewStudent:​ Prompt the user to enter name, last name and id of the new student.Values entered by the user are assigned to the fields of the student residing in themyStudentArray ​of course variable pointed by ​myCourse​. ​currentStudentCount ​will be updated so that it designates the slot allocated for the student inserted next.
and my implementation:
#include <string.h>
#include <stdio.h>
struct Student {
char name[50];
char lastname[50];
int id;
int mid1;
int mid2;
int final;
double average;
};
struct Course {
char courseName[50];
char courseCode[50];
struct Student myStudentArray[5];
int currentstudentcount;
};
void createNewStudent(struct Course * myCourse);
void setGradeOfStudent(struct Course * myCourse);
void findAndDisplayAverage(struct Course * myCourse);
struct Student * findStudentByID(int id, struct Course * myCourse);
void displayAverageOfAllStudents(struct Course * myCourse);
void displayAverageOfStudentsInInterval(struct Course * myCourse);
int main() {
struct Student * stud;
int input = 0;
scanf("%d", & input);
if (input == 1) {
createNewStudent(struct Course * myCourse);
}
}
return 0;
}
void createNewStudent(struct Course * myCourse) {
struct Student s1;
printf("Enter name: ");
scanf("%[^\n]%*c", s1.name);
printf("Enter Surname: ");
scanf("%[^\n]%*c", s1.lastname);
printf("Enter id: ");
scanf("%d", & s1.id);
}
When you call the function with the if(input == 1) it gives
error: expected expression before ‘struct’
but I dont understand this beacuse *myCourse is just a pointer to the Course struct isn't it ????
If I can understand this ı will be able to the the next functions I think
Is the function correct ?? I dont know why this doesnt work
Ok I tried to use the struct Student myStudentArray[5]; to get name, lastname,id like so (structs are the same)
void createNewStudent(struct Course *myCourse);
void setGradeOfStudent(struct Course *myCourse);
int main(){
struct Course *myCourse;
int input=0;
scanf("%d",&input);
if(input == 1){
createNewStudent(myCourse);
}
return 0;
}
void createNewStudent(struct Course *myCourse){
myCourse->currentstudentcount=0;
printf("Enter name: ");
scanf("%[^\n]%*c"
,myCourse->myStudentArray[myCourse->currentstudentcount].name);
printf("Enter Surname: ");
scanf ("%[^\n]%*c",
myCourse->myStudentArray[myCourse->currentstudentcount].name);
myCourse->currentstudentcount++;
}
I Keep getting
may be used uninitialized in this may be used uninitialized in this function [-Wmaybe-uninitialized]
and
Segmentation errors
void createNewStudent(struct Course * myCourse)
If you want to create new student, you should use the student struct as the parameter of this function instead of using struct Course.
void createNewStudent(struct Student *s1)
Then, this function becomes as:
void createNewStudent(struct Student *s1) {
printf("Enter name: ");
scanf("%49s", s1->name);
printf("Enter Surname: ");
scanf("%49s", s1->lastname);
printf("Enter id: ");
scanf("%d", & s1->id);
}
If you want to test, in main function, you can declare the value stud or the pointer to struct Student.
For example:
int main() {
struct Student stud;
int input = 0;
scanf("%d", & input);
if (input == 1) {
createNewStudent(&stud);
printf("name: %s\n Surname: %s\n id = %d\n", stud.name, stud.lastname, stud.id);
}
return 0;
}
The complete program for test:
#include <string.h>
#include <stdlib.h>
#include <stdio.h>
struct Student {
char name[50];
char lastname[50];
int id;
int mid1;
int mid2;
int final;
double average;
};
struct Course {
char courseName[50];
char courseCode[50];
struct Student myStudentArray[5];
int currentstudentcount;
};
void createNewStudent(struct Student *s1);
int main() {
struct Student stud;
int input = 0;
scanf("%d", & input);
if (input == 1) {
createNewStudent(&stud);
printf("name: %s\nSurname: %s\nid = %d\n", stud.name, stud.lastname, stud.id);
}
return 0;
}
void createNewStudent(struct Student *s1) {
printf("Enter name: ");
scanf("%49s", s1->name);
printf("Enter Surname: ");
scanf("%49s", s1->lastname);
printf("Enter id: ");
scanf("%d", & s1->id);
}
The output:
#./test
1
Enter name: abc
Enter Surname: def
Enter id: 100
name: abc
Surname: def
id = 100
Update for your question in the comment:
If you want to store student info in an array, you can change the code to:
struct Student myStudentArray[5];
int input = 0;
scanf("%d", & input);
if (input == 1) {
for (int i = 0; i < 5; i++) {
createNewStudent(&myStudentArray[i]);
}
for (int i = 0; i < 5; i++) {
printf("name: %s\nSurname: %s\nid = %d\n", myStudentArray[i].name, myStudentArray[i].lastname, myStudentArray[i].id);
}
}
For Course structure you can create one function as the function createNewStudent but for struct Course to create the new course. After creating new 5 students (for example the code above), you can copy the myStudentArray to new_course.myStudentArray. Then now you have the info of 5 students in new_course. When you copy value from an array to another, you can use memcpy or using one loop to copy each element from one array to another one. Do not use something like myStudentArray = new_course.myStudentArray for the array.
You are making a declaration as a parameter of the createNewStudent() function. In C, functions require expressions as parameters, which is why you got the error message "expected expression...".
So, just create the struct pointer before you call the function:
if (input == 1) {
struct Course *myCourse = malloc(sizeof(struct Course));
createNewStudent(myCourse);
}
Notice the use of malloc(), which returns a pointer to a place in memory of sufficient size to hold that particular Course struct. When dealing with pointers to structs, you need to allocate memory for the structs that will ultimately be pointed to, in order to avoid dereferencing unallocated regions of memory.
In your function CerateNewStudent, the proper way to address the variables into which to place the data read by scanf should be:
myCourse->myStudentArray[myCourse->currentstudentcount].name
as the variable to read name into. Use this syntax for all data items to read. After that, increment the counter:
myCourse->currentstudentcount++;
Note: what is missing in all your functions (and in the assignment?) is a way to create a course. The students created are all added to courses. First a course should be created and then students can be added to it.

How to fill in values in struct using a function?

I want to call a function to fill in the values of a struct in C. I have the following code but I get errors like [Error] request for member 'id' in something not a structure or union.
#include <stdio.h>
typedef struct {
int id;
float grades[3];
} student_t;
void scan_student (student_t *s) {
printf("Please give student's info:\n");
scanf("%d%f%f%f", s.id, s.grades[0], s.grades[1], s.grades[2]);
}
int main ()
{
student_t stu2;
scan_student(&stu2);
printf("Student's info are:\n");
printf("%6d %5.2f %5.2f %5.2f\n", stu2.id, stu2.grades[0], stu2.grades[1], stu2.grades[2]);
return 0;
}
s is a pointer, not a struct. That means you can't use . on it.
Instead you have to write (*s).id (dereference, then access struct member) or s->id (same thing, but shorter).
Also, scanf %d takes a pointer, so that should be &s->id, etc.
I also post an example without using pointers:
#include <stdio.h>
typedef struct {
int id;
float grades[3];
} student_t;
student_t scan_student () {
student_t s;
printf("Please give patient's info:\n");
scanf("%d%f%f%f", &s.id, &s.grades[0], &s.grades[1], &s.grades[2]);
return s;
}
int main ()
{
student_t stu2;
stu2= scan_student();
printf("Student's info are:\n");
printf("%6d %5.2f %5.2f %5.2f\n", stu2.id, stu2.grades[0], stu2.grades[1], stu2.grades[2]);
return 0;
}

Problems with C structs and int variables

#include <stdio.h>
#include "struct.h"
#define NUM 3
struct Student
{
char name[20];
int age;
};
int main(void)
{
struct Student s_array[NUM];
for(int i=0;i<NUM;i++)
{
printf("name: ");
scanf("%s",s_array[i].name);
printf("age: ");
scanf("%i",s_array[i].age);
}
for(int i=0;i<NUM;i++)
{
printf("%s is %i years old",s_array[i].name,s_array[i].age);
}
return 0;
}
I don't know what's the problem I declared an array of structs of type student and used a for loop to initialise their fields, but when I type in the age it gives me segmentation fault. why is that??
struct.c:17:20: warning: format specifies type 'int *' but the argument has type 'int' [-Wformat]
scanf("%d",s_array[i].age);
The int in the struct is an int, not a pointer to an int. Arrays can be assigned directly to pointers, but on other types, you need to apply the addressof (&) operator. Instead of saying "s_array[i].age", say "&(s_array[i].age)".
I worked out this code for you
#include < stdio.h>
#include < stdlib.h>
#define NUM 3
struct Student
{
char name[20];
int age;
};
int main(void)
{
struct Student s_array[NUM];
for(int i=0;i<NUM;i++)
{
printf("name: ");
scanf("%s",&s_array[i].name);
printf("age: ");
scanf("%d",&s_array[i].age);
}
for(int i=0;i<NUM;i++)
{
printf("%s is %d years old",s_array[i].name,s_array[i].age);
}
return 0;
}
#include<stdio.h>
//#include "struct.h>
#define NUM 3
struct Student
{
char name[20];
int age;
};
int main(void)
{
struct Student s_array[NUM];
for(int i=0;i<NUM;i++)
{
printf("name: ");
scanf("%s",&s_array[i].name);
printf("age: ");
scanf("%d",&s_array[i].age);//You sud use "&"operator to take input
}
for(int i=0;i<NUM;i++)
{
printf("%s is %d years old",s_array[i].name,s_array[i].age);
}
return 0;
}

nested structures in C

goal: ask user for the number of agencies, create said agencies, and for each agency ask for the number of employees, and create those employees.
part of this will require, I think, nested structure, something like
typedef struct agence agence;
struct agence
{
char nom[20];
int nmbrEmp;
struct employe
{
char mat[20];
int nmbrEnf;
int ANC;
double SB;
double RCNSS;
}
};
is this n the right path, and how do you proceed to create the number of agencies/employees once the users gives you the number required of each.
C unlike C++ cannot have nested types, you will have to declare them separately.
struct employe
{
char mat[20];
int nmbrEnf;
int ANC;
double SB;
double RCNSS;
};
struct agence
{
char nom[20];
int nmbrEmp;
struct employe * employees; // pointer to an array of employees
};
Then use dynamic memory and populate them:
struct agence * agencies;
size_t num_agencies = 100;
agencies = calloc(sizeof(*agencies), num_agencies);
for (/* read egancies somehow */) {
agencies[i].nmbrEmp = number_employees;
agencies[i].employees = calloc(sizeof(agencies[i].employees[0]), number_employees);
// write agencies[i].employees[j] ...
}
Consider this Example :
struct Employee
{
char ename[20];
int ssn;
float salary;
struct date
{
int date;
int month;
int year;
}doj;
}emp1;
Accessing Nested Members :
Accessing Month Field : emp1.doj.month
Accessing day Field : emp1.doj.day
Accessing year Field : emp1.doj.year
Here is the Code pad which will demonstrate the above example
enter link description here
In c, you cannot have unnamed nested structures [otherwise, nested types]. They have to be a named structure. You need to write something like
typedef struct agency
{
char nom[20];
int nmbrEmp;
struct employee
{
char mat[20];
int nmbrEnf;
int ANC;
double SB;
double RCNSS;
} emp [20];
}agency;
However, here you are limited to the static input of a size 20, that means, you cannot have more than 20 employee records. To liberate from this limitation , the best approach is to use a pointer to an employee structure, an in runtime, allocate memory based on the number of the employee given by the user.
Here's an example you might consider. This is a template of what you have to do, you are left with manipulating employees, agencies name and so on. (Note that there's no error checking, which is bad.)
#include <stdio.h>
#include <stdlib.h>
/* TODO: modify members */
typedef struct {
int id;
int salary;
} employee;
/* TODO: modify members */
typedef struct {
char name[20];
employee* emps;
int emps_count;
} agency;
/* return sum of id and salary for first employee from agency */
int dumb_calc(agency ag) {
return ag.emps[0].id + ag.emps[0].salary;
}
int main(void)
{
int num_ag;
int num_emps;
int i, j;
printf("enter num of agencies:\n");
scanf("%d", &num_ag);
agency* agencies = malloc(sizeof(agency) * num_ag);
for (i = 0; i < num_ag; ++i) {
/* TODO: modify single agency name */
sprintf(agencies[i].name, "agency %d", i+1);
printf("enter num of employees for agency %d\n", i+1);
scanf("%d", &num_emps);
agencies[i].emps = malloc(sizeof(employee) * num_emps);
agencies[i].emps_count = num_emps;
for (j = 0; j < num_emps; ++j) {
/* TODO: modify single employee */
agencies[i].emps[j].id = j+1;
agencies[i].emps[j].salary = 1000*(j+1);
}
}
/* TODO: change printing style */
for (i = 0; i < num_ag; ++i) {
printf("agency name: %s\n", agencies[i].name);
printf("num of employees: %d\n", agencies[i].emps_count);
/* result will always be the same */
printf("sum of id and salary for 1st emp: %d\n", dumb_calc(agencies[i]));
}
/* remember to free what you've alloc'd */
for (i = 0; i < num_ag; ++i) {
free(agencies[i].emps);
}
free(agencies);
return 0;
}

Am I using structs in the wrong way?

I have come across this wierd and mysterous (at least to me) error that I am finding a very hard time finding. It gives me an error at the line where I call my function input(student_list1[MAX], &total_entries); where the compiler says:
incompatible type for agument 1 in 'input'
What am I doing wrong here? I sense it something very simple and stupid but I have gone through the code several times now without any avail.
#define MAX 10
#define NAME_LEN 15
struct person {
char name[NAME_LEN+1];
int age;
};
void input(struct person student_list1[MAX], int *total_entries);
int main(void)
{
struct person student_list1[MAX];
int total_entries=0, i;
input(student_list1[MAX], &total_entries);
for(i=0; i<total_entries; i++)
{
printf("Student 1:\tNamn: %s.\tAge: %s.\n", student_list1[i].name, student_list1[i].age);
}
return 0;
} //main end
void input(struct person student_list1[MAX], int *total_entries)
{
int done=0;
while(done!=1)
{
int i=0;
printf("Name of student: ");
fgets(student_list1[i].name, strlen(student_list1[i].name), stdin);
student_list1[i].name[strlen(student_list1[i].name)-1]=0;
if(student_list1[i].name==0) {
done=1;
}
else {
printf("Age of student: ");
scanf("%d", student_list1[i].age);
*total_entries++;
i++;
}
}
}
struct person student_list1[MAX] in the function argument is actually a pointer to struct person student_list1.
student_list1[MAX] you passed is a (out of bound) member of the array struct person student_list1[MAX]. Valid array index shoudl be between 0 to MAX - 1.
Change it to:
input(student_list1, &total_entries);
Note that here the array name student_list1 is automatically converted to a pointer to student_list1[0].
There are many things wrong with the code; this is my attempt at making it somewhat more robust:
#include <stdio.h>
#include <string.h>
#define MAX 10
#define NAME_LEN 15
// use a typedef to simplify code
typedef struct person {
char name[NAME_LEN];
int age;
} person_t;
// size qualifier on student_list is redundent and person_t* does the same
void input(person_t *student_list, int *total_entries);
int main(void)
{
person_t student_list[MAX];
int total_entries, i;
// pass array and not the non-existent 'student_list[MAX]' element
input(student_list, &total_entries);
for(i=0; i<total_entries; i++)
{
// age is an int, not a string so use %d
printf("Student 1:\tName: %s.\tAge: %d.\n", student_list[i].name, student_list[i].age);
}
return 0;
} //main end
void input(person_t *student_list, int *total_entries)
{
int done = 0, i = 0;
*total_entries = 0;
while (i < MAX) {
printf("Name of student: ");
// use NAME_LEN instead of strlen(list[i].name) because latter is
// probably not initialized at this stage
if (fgets(student_list[i].name, NAME_LEN, stdin) == NULL) {
return;
}
// detect zero-length string
if (student_list[i].name[0] == '\n') {
return;
}
printf("Age of student: ");
scanf("%d", &student_list[i].age);
// read the newline
fgetc(stdin);
*total_entries = ++i;
}
}
input(student_list1[MAX], &total_entries); shoud be input(student_list1, &total_entries);.
In C,
void input(struct person student_list1[MAX], int *total_entries);
equals
void input(struct person *student_list1, int *total_entries);

Resources