I am having a problem with this code:
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
int main(void)
{
int num=0;
printf("Enter number of entries: ");
scanf_s("%d", &num);
char **firstname=NULL;
char **lastname=NULL;
float *score=NULL;
int i;
firstname = malloc(num * (sizeof(char*)));
for (i = 0; i < num; i++)
{
firstname[i] = malloc(21);
}
lastname = malloc(num * (sizeof(char*)));
for (i = 0; i < num; i++)
{
lastname[i] = malloc(21);
}
score = ((float*)malloc(num* (sizeof(float))));
for (i = 1; i <= num; i++)
{
printf("Enter the first name of entry %d: \n", i);
scanf_s("%s", firstname[i], 21);
printf("Enter the last name of entry %d: \n", i);
scanf_s("%s", lastname[i], 21);
printf("Enter the score of entry %d: \n", i);
scanf_s("%f", score[i]);
}
for (i = 0; i < num; ++i)
{
printf("%s, %s, %f", firstname[i], lastname[i], score[i]);
}
return 0;
}
I have edited the code with the suggested changes, and now it prints random characters and a random value for the first and last name, as well as the score. the code also crashes if there is more than one iteration of input (after asking for the score of the first entry, it crashes before asking for the first name of the second entry.)
Related
int const size = 100;
float grades[size];
char students[size][size];
char temp_students[size][size];
int main() {
int length = 0;
int i = 0;
float g = 0;
printf("How many students do you want to enter? \n ");
scanf("%d", &length);
while((i < length)){
printf("Enter the name and grade \n");
// scanf("%s", students[i]);
char temp;
scanf("%c",&temp); // temp statement to clear buffer
scanf("%[^\n]", students[i]);
strcpy(temp_students[i], students[i]);
printf("Enter the grade again \n");
scanf(" %f", &g);
grades[i] = g;
insertion_sort_float(grades, g, length);
insertion_sort_string(students, students[i], length);
i++;
}
i--;
print_report(grades, students, length);
}
void print_report(float grades[], char students[size][size], int number){
printf("Students Test Report \n");
printf("Students that took the test: %d \n", number);
for (int i = 0; i < number; i++){
for(int j = 0; j < number; j++){
printf("%c", students[i][j]);
}
printf("\n");
}
double average = average_number(grades, number);
double median = median_number(grades, number);
double highest = max_number(grades, number);
double lowest = min_number(grades, number);
printf("Average: %f \n Median: %f \n Highest: %f \n Lowest: %f \n", average, median, highest, lowest);
}
void insertion_sort_string(char students[size][size], char string[], int array_size) {
if (array_size+ 1 < size) {// only do insert when there is free space in array
if (array_size == 0)//empty array, insert at the top directly
strcpy(students[0], string);
int insert_index;//to identify the location
for (int i = 0; i < array_size + 1; i++) {
insert_index = i;
if (strcmp(students[i], string)) // due the sorted property of array,
break;// where the first bigger item showes up, where we should insert
}//end of the first for loop
// if we don't find any bigger item, inset_index will equal to element_num, which means we insert at the tail
for (int j = array_size; j > insert_index; j--) {
strcpy(students[j], students[j-1]);
}// end of the second loop
strcpy(students[insert_index], string); // do the insert
} else {
printf("overflow!");
return;
}
}
This is what happens when the code is run:
Write a program that allows a user to enter the names of students that took a test along with the grades they received.
I am not sure why none of the other names are being stored. Only Gerar is being printed. Also the entire string should be printed: "Gerard 78.5", but that is not happening either.
Some code omitted for post purposes. But important code is included
function gets an array of grades and changes the amount of grades if there are less elements than before the function will delete those elements
for example: before: I entered in another function 3 grades: 100, 90, 80.
after: In this function it asked me to enter new amount, and I entered, and then entered it's grade, 70.
after I return it to the main and sending the array, grades, to a function which prints the array and it's stays with 3 elements, 100, 90, 80.
please help me i tried a lot of time and didn't succeed.
void changeNumOfGrades(int* grades, int size)
{
int numOfGrades = 0;
int i = 0;
do
{
if (i > ONE_ITERATION)
{
printf("Please enter positive number...\n");
}
printf("How many elements would you like? ");
scanf("%d", &numOfGrades);
i += 1;
} while (numOfGrades < 0);
grades = realloc(grades, numOfGrades*sizeof(int));
if (!grades)
{
printf("Unsuccessful realloc");
//There is no need to release memory because the realloc is for the same pointer.
}
if (numOfGrades > size)
{
printf("You have more grades than before,\nPlease enter their grades: \n");
int newGrade = 0;
//int newNumOfGrades = numOfGrades - size;
int i = 0;
for (i = size + 1; i <= numOfGrades; i++)
{
printf("Enter grade number %d: ", i);
scanf("%d", &newGrade);
*(grades + i - 1) = newGrade;
printf("hey %d", *(grades + 1));
}
}
}
In order for you to reallocate grades, you need to pass as **grades.
For test reasons, I have changed size to get the new allocation size, so you can print the array after the changeNumOfGrades
void changeNumOfGrades(int** grades, int *size/*get new size*/)
{
int numOfGrades = 0;
int i = 0;
do
{
if (i > ONE_ITERATION)
{
printf("Please enter positive number...\n");
}
printf("How many elements would you like? ");
scanf("%d", &numOfGrades);
i ++;
} while (numOfGrades < 0);
printf("%d",numOfGrades);
*grades = realloc(*grades, numOfGrades*sizeof(int));/*realloc **grade */
if (!grades)
{
printf("Unsuccessful realloc");
//There is no need to release memory because the realloc is for the same pointer.
}
printf("...\n");
if (numOfGrades > *size)
{
printf("You have more grades than before,\nPlease enter their grades: \n");
int newGrade = 0;
//int newNumOfGrades = numOfGrades - size;
int i = 0;
for (i = *size + 1; i <= numOfGrades; i++)
{
printf("Enter grade number %d: ", i);
scanf("%d", &newGrade);
*(*grades + i - 1) = newGrade;
//printf("hey %d", *(grades + 1));
}
}
*size = numOfGrades;/*get new size allocated*/
}
void main()
{
int numOfInts;
int *grades ;
grades = malloc(3*sizeof(int));
memset(grades,0,sizeof(int)*3);
grades[0]=100;
grades[1]=80;
grades[2]=20;
numOfInts = 3;/*initialize 3 items*/
changeNumOfGrades(&grades,&numOfInts);
printf("\n\n");
for (int i=0;i<numOfInts;i++)
{
printf("%d\n",grades[i]);
}
free(grades);
}
I've been studying C for almost three months now and I neved had much trouble on the way. However, I have this task to create a program that will arrange an array of products (chosen by the user), either by their price or their available quantity.
I had to use a struct called Product to do so. Problem is, when I enter on any of the functions (arrangePrice or arrangeQuantity), the console prints the "What is the name of product?" printf command and IMMEDIATELY prints out the "What is the price of the product?" printf command. It simply seems to ignore the scanf function between those commands that would let the user write the name of the product on a string. Why is that happening???
Here is the entire code:
#include <stdio.h>
#include <string.h>
struct Product
{
char name[80];
double price;
int quantity;
};
void arrangePrice(struct Product vet[], int n)
{
int i, j, auxQuant;
double aux, auxprice;
char auxname[80];
for (i = 0; i < n; i++)
{
printf("What is the name of the product?\n");
scanf("%[^\n]", vet[i].name);
printf("What is the price of the product?\n");
scanf("%lf", &vet[i].price);
printf("What is the available quantity of the product?\n");
scanf("%d", &vet[i].quantity);
}
printf("\n\nArranging by price:\n\n");
for (j = 0; j < n; j++)
{
aux = vet[j].price;
for (i = j + 1; i < n; i++)
{
if (vet[i].price < aux)
{
auxprice = vet[i].price;
strcpy(auxname, vet[i].name);
auxQuant = vet[i].quantity;
vet[i] = vet[j];
strcpy(vet[j].name, auxname);
vet[j].price = auxprice;
vet[j].quantity = auxQuant;
}
}
}
for (i = 0; i < n; i++)
{
printf("%[^\n] -> %.2lf\n", vet[i].name, vet[i].price);
}
}
void arrangeQuant(struct Product vet[], int n)
{
int i, j, aux, auxQuant;
double auxprice;
char auxname[80];
for (i = 0; i < n; i++)
{
printf("What is the name of the product?\n");
scanf("%[^\n]", vet[i].name);
printf("What is the price of the product?\n");
scanf("%lf", &vet[i].price);
printf("What is the available quantity of the product?\n");
scanf("%d", &vet[i].quantity);
}
printf("\n\nArranging by available quantity:\n\n");
for (j = 0; j < n; j++)
{
aux = vet[j].quantity;
for (i = j + 1; i < n; i++)
{
if (vet[i].quantity < aux)
{
auxprice = vet[i].price;
strcpy(auxname, vet[i].name);
auxQuant = vet[i].quantity;
vet[i] = vet[j];
strcpy(vet[j].name, auxname);
vet[j].price = auxprice;
vet[j].quantity = auxQuant;
}
}
}
for (i = 0; i < n; i++)
{
printf("%[^\n] -> %d\n", vet[i].name, vet[i].quantity);
}
}
int main()
{
struct Product prod[51];
int n;
int choice;
printf("How many products will be added? (Maximum of 50)\n");
scanf("%d", &n);
while (n < 1 || n > 50)
{
printf("Invalid value. Try again.\n");
scanf("%d", &n);
}
printf("Do you want to arrange by price or by available quantity? (0 or 1)\n");
scanf("%d", &choice);
if (choice == 0) arrangePrice(prod, n);
else if (choice == 1) arrangeQuant(prod, n);
else printf("Invalid value.\n");
return 0;
}
I must say that I actually still don't know if the code is right or not, since I couldn't type the name of the products. Thanks for any help!
Your scanf calls are leaving newline characters in the input buffer, and those newlines are being read on subsequent calls.
You need to leave a space at the start of each scanf pattern to consume any newlines that may be left over.
Also, %[^\n] is not a valid format specifier for printf. Use %s instead.
Example:
printf("What is the name of the product?\n");
scanf(" %s", vet[i].name); // use %s for strings
printf("What is the price of the product?\n");
scanf(" %lf", &vet[i].price);
printf("What is the available quantity of the product?\n");
scanf(" %d", &vet[i].quantity);
And:
printf("How many products will be added? (Maximum of 50)\n");
scanf(" %d", &n);
while (n < 1 || n > 50)
{
printf("Invalid value. Try again.\n");
scanf(" %d", &n);
}
printf("Do you want to arrange by price or by available quantity? (0 or 1)\n");
scanf(" %d", &choice);
struct product vet[] is a pointer. It doesn't actually point to an array unless you allocate such an array before you call arrangePrice. For example:
struct Product vet_array[ 2 ];
arrangePrice( vet_array, 2 );
Alternatively you could call malloc but just to get this started to work, allocate a local on the stack with a fixed number of elements.
The goal of my code is to have the user, put in any amount of students as an integer and then have the program ask over and over to set a name too every integer (student)
I've been trying so many different things and I've been working on this without using any outside help for hours but I just couldn't figure this out. (if its something obvious, please don't get supermad, I'm only a beginner)
#include <cs50.h>
#include <string.h>
#include <stdio.h>
int main (void)
{
printf("How many students are there? ");
int amount = atoi(GetString());
printf("amount = %i\n", amount);
char *names[amount];
for(int i = 0; i < amount; i++)
{
printf("Enter the ellement #%d :", i +1);
scanf("%s", names[i]);
}
for (int i = 0; i == 0;)
{
printf("Acces student: ");
string search = GetString();
int searchnr = atoi(search);
printf("Student #%d is %s\n", searchnr, names[searchnr]);
}
}
>
}
The obvious solution:
for (int i = 0; i < amount; i++) {
printf("Enter element #%d: ", i + 1);
names[i] = GetString();
}
As to the second loop: it's an infinite loop. What is the terminating condition? You need to put that into the condition of the for loop else it will never terminate.
If your intent is getting an infinite loop, then a more readable, less confusing, more idiomatic solution is
while (1) {
// ...
}
or
for (;;) {
// ...
}
You need to reserve space for those strings:
char *names[amount];
char s[100];
for(int i = 0; i < amount; i++)
{
printf("Enter the ellement #%d :", i +1);
scanf("%s", s);
names[i] = strdup(s);
}
or
char *names[amount];
char s[100];
size_t len;
for(int i = 0; i < amount; i++)
{
printf("Enter the ellement #%d :", i +1);
scanf("%s", s);
len = strlen(s);
names[i] = malloc(len + 1);
strcpy(names[i], s);
}
And this for loop:
for (int i = 0; i == 0;)
does nothing, what do you want to do? (if you want to loop forever you can use for(;;))
Using malloc
char temp[50];
for(int i = 0; i < amount; i++)
{
printf("Enter the ellement #%d :", i +1);
scanf("%s", temp);
names[i]=malloc(strlen(temp)+1);
strcpy(names[i],temp);
}
Using strdup
char temp[50];
for(int i = 0; i < amount; i++)
{
printf("Enter the ellement #%d :", i +1);
scanf("%s", temp);
names[i] = strdup(temp);
}
All your answers were great guys, but this was the final solution:
#include <cs50.h>
#include <string.h>
#include <stdio.h>
int main (void)
{
printf("How many students are there? ");
int amount = atoi(GetString());
char *names[amount];
for(int i = 0; i < amount; i++)
{
printf("Enter the ellement #%d :", i +1);
names[i + 1] = GetString();
}
for (int i = 0; i == 0;)
{
printf("Acces student: ");
int search = atoi(GetString());
printf("Student #%d is %s\n", search, names[search]);
}
}
and I know I have an infinite loop there, that was just temporary so I don't have to rerun the command all the time.
This is a homework problem. I have a C program that takes user input for a number of people's first names, last names, and ages. Right now it works and prints out the names to the console correctly, but it is not printing out the right ages, and I can't figure out what I'm doing wrong. Here's my code:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main()
{
int choice;
int i = 0;
int x,k,l;
fputs("How many people would you like to add? ", stdout);
scanf(" %d", &choice);
fflush(stdout);
int ch;
while((ch = getchar()) != EOF && ch != '\n');
if (ch == EOF)
{
}
char firstName[choice][20];
char lastName[choice][20];
int age[choice][3];
char first[20];
char last[20];
int a[3];
for (x = 0; x < choice; x++)
{
for (l = 0; l < 3; l++)
{
age[x][l] = 0;
a[l] = 0;
}
}
while(i < choice)
{
printf("Enter the first name of person ");
printf(" %d", i);
printf(": ");
fgets(first, 20, stdin);
for (k = 0; k < 20; k++)
{
firstName[i][k] = first[k];
}
i++;
}
i = 0;
while(i < choice)
{
printf("Enter the last name of person ");
printf(" %d", i);
printf(": ");
fgets(last, 20, stdin);
for (k = 0; k < 20; k++)
{
lastName[i][k] = last[k];
}
i++;
}
i = 0;
while(i < choice)
{
fputs("Enter the age of person ", stdout);
printf(" %d", i);
printf(": ");
scanf(" %d", &a);
fflush(stdout);
for (l = 0; l < 3; l++)
{
age[i][l] = a[l];
}
i++;
}
int sh;
while((sh = getchar()) != EOF && sh != '\n');
if (sh == EOF)
{
}
for (x = 0; x < choice; x++)
{
printf("First name ");
printf(": ");
printf("%s ", firstName[x]);
printf("\n");
printf("Last name ");
printf(": ");
printf("%s ", lastName[x]);
printf("\n");
printf("Age ");
printf(": ");
printf("%d ", &age[x]);
printf("\n");
}
return 0;
}
If you copy/paste this code it will run, but the age outputted will be incorrect. Can anyone tell me why this is? Thank you!
scanf(" %d", &a);
That should be:
scanf(" %d", &a[0]);
And the printf should be printf("%d", age[x][0]);
You want to read into the first element of the array, not the entire array. You want to print out the first element of the array, not the address of the array.
A better solution would probably be not to make age an array of 3 at all. Each person only has one age. The changes would be:
int age[choice];
int a;
scanf(" %d", &a);
age[choice] = a;
printf("%d ", age[x]);