我是C的新手程序员,我遇到了一个几乎非常简单的问题。我正在编写一个基本程序,它创建两个数组,一个学生名和一个学生ID号,然后对它们进行排序并以各种方式打印它们,最后允许用户按ID号搜索数组。这是代码:
#include <stdio.h>
#include <string.h>
#define ARRAY_SIZE 3
#define MAX_NAME_LENGTH 32
int main()
{
// Student info arrays
char NAME[ARRAY_SIZE][MAX_NAME_LENGTH];
int ID[ARRAY_SIZE];
// Array for student IDs, shifted twice to the right
int shiftedID[ARRAY_SIZE];
// Boolean value to keep while loop running and
// the ID search prompt repeating
int loop = 1;
// Counter variable for the for loop
int counter;
// Gets input values for the student info arrays
for (counter = 0; counter < ARRAY_SIZE; counter++)
{
printf("Input student name: ");
scanf("%s", NAME[counter]);
printf("Input student ID: ");
scanf("%d", &ID[counter]);
}
// Sorts the arrays
sort(NAME, ID);
// Prints the arrays
print_array(&NAME, ID);
// Shifts the ID value two bits to the right
shiftright(ID, shiftedID);
print_array(NAME, shiftedID);
// Repeatedely prompts the user for an ID to
// search for
while(loop == 1)
{
search_id(NAME, ID);
}
}
以下是函数定义:
#define ARRAY_SIZE 3
#define MAX_NAME_LENGTH 32
// Sorts the two arrays by student ID. (Bubble sort)
void sort(char **nameArray, int idArray[])
{
// Counter variables for the for loop
int firstCounter = 0;
int secondCounter = 0;
for(firstCounter = 0; firstCounter < ARRAY_SIZE; firstCounter++)
{
for(secondCounter = 0; secondCounter < ARRAY_SIZE - 1;
secondCounter++)
{
if(idArray[secondCounter] > idArray[secondCounter + 1])
{
// Temporary variables for the sort algorithm
int tempInt = 0;
char tempName[32];
tempInt = idArray[secondCounter + 1];
idArray[secondCounter + 1] = idArray[secondCounter];
idArray[secondCounter] = tempInt;
strcpy(tempName, nameArray[secondCounter + 1]);
strcpy(nameArray[secondCounter + 1],
nameArray[secondCounter]);
strcpy(nameArray[secondCounter], tempName);
}
}
}
}
// Searches the ID array for a user input student
// ID and prints the corresponding student's info.
void search_id(char **nameArray, int idArray[])
{
// A boolean value representing whether or not
// the input ID value was found
int isFound = 0;
// The input ID the user is searching for
int searchID = 0;
printf("Input student ID to search for: ");
scanf("%d", &searchID);
// Counter variable for the for loop
int counter = 0;
while (counter < ARRAY_SIZE && isFound == 0)
{
counter++;
if (idArray[counter] == searchID)
{
// Prints the name associated with the input ID
isFound = 1;
printf("%s", nameArray[counter]);
}
}
// If the input ID is not found, prints a failure message.
if (isFound == 0)
{
printf("ID not found.\n");
}
}
// Prints the name and ID of each student.
void print_array(char **nameArray, int idArray[])
{
// Counter variable for the for loop
int counter = 0;
printf("Student Name & Student ID: \n");
for (counter = 0; counter < ARRAY_SIZE; counter++)
{
printf("%s --- %d\n", nameArray[counter], idArray[counter]);
}
}
// Shifts the ID value to the right by two bits
void shiftright(int idArray[], int shiftedID[])
{
// Counter variable for the for loop
int counter = 0;
for (counter = 0; counter < ARRAY_SIZE; counter++)
{
shiftedID[counter] = idArray[counter] >> 2;
}
}
我知道这个程序本质上是相当基础的,而且最重要的是让我更精通C语言的练习。我已经研究了一段时间了,并且已经工作了通过几个问题,但似乎坚持三个问题:
如果输入的ID号没有按顺序输入,则会产生分段错误。如果ID编号已经按顺序输入,则sort函数永远不会通过if语句,也不会出现问题。
将名称/ ID数组传递给print_array函数时,ID打印得很好,但名称将打印为完全空白或一系列奇怪的字符。
在程序结束时按ID搜索时,首先输入的ID号(因此,ID [0]中的数字)显示ID not found消息,其中索引为1或更大的所有数字将正常工作 - 除了应打印的相应名称打印为空白,如第二期中所述。
我将非常感谢您能得到的任何建议!我发现C中所需的精细细节背后的力量既非常有趣,又非常令人困惑,令人生畏,这意味着我能得到的任何帮助都会产生很大的不同。
答案 0 :(得分:5)
问题在于您假设char [ARRAY_SIZE][MAX_NAME_LENGTH]
和char **
可以互换
void sort(char **nameArray, int idArray[])
应该是
void sort(char nameArray[][MAX_NAME_LENGTH], int idArray[])
或
void sort(char (*nameArray)[MAX_NAME_LENGTH], int idArray[])
为了使用指向MAX_NAME_LENGTH
char
s数组的指针,对search_id
函数使用相同的指针。
答案 1 :(得分:2)
我建议你重组你的程序。您可以存储一个包含所有必要数据的结构数组,而不是为名称和ID存储两个独立的数组:
typedef struct student
{
int id;
char name[MAX_NAME_LENGTH];
} student_t;
student_t students[ARRAY_SIZE];
现在你有一个单独的数组,通过排序没有名称等的ID,永远不会“不匹配”。
您可以使用标准库函数qsort()
在
qsort(students, ARRAY_SIZE, sizeof(student_t), comparator);
这需要你定义一个比较器,这很简单。一个例子是:
int comparator(const void *lhs, const void *rhs)
{
const student_t *s1 = lhs, *s2 = rhs;
return s1->id - s2->id;
}
您可以将同一个比较器与另一个标准库函数bsearch()
一起使用,以便在排序后搜索学生数组:
student_t key = { 42 }; // name doesn't matter, search by ID
student_t* result = bsearch(&key, students, ARRAY_SIZE, sizeof(student_t), comparator);
这些标准函数比你的函数更有效,并且要求你编写更少的代码,错误的机会更少。