使用 strtok 从文件中获取输入
using strtok to get input from file
我正在尝试创建一个程序,该程序从一个文件中获取多个进程(名称、开始时间、剩余时间),然后使用循环算法来处理队列。
问题是,当我尝试使用 strtok()
和 fgets()
对文件的每一行进行标记时,进程名称总是错误的。
例如,如果第一行是 P1 0 3
输出是这样的:
void RoundRobin(char *filename) {
Queue *q = initQueue();
char string[MAX_SIZE];
FILE *file;
Process process[20];
char *token;
file = fopen(filename, "r");
if (!file) {
printf("File Cannot Be Opened");
}
fgets(string, 150, file);
token = strtok(string, "=");
token = strtok(NULL, "+");
int time_quantum = atoi(token);
int process_count = 0;
while (fgets(string, 150, file)) {
char *token1;
token1 = strtok(string, " ");
process[process_count].name = token1;
token1 = strtok(NULL, " ");
process[process_count].starting_time = atoi(token1);
token1 = strtok(NULL, " ");
process[process_count++].remaining_time = atoi(token1);
token1 = strtok(NULL, " ");
}
for (int i = 0; i < process_count; i++) {
printf("%s %d %d\n", process[i].name, process[i].starting_time, process[i].remaining_time);
}
fclose(file);
}
您正在为所有令牌解析重复使用单个 char[]
。 fgets()
每次都会覆盖 char[]
的内容,而 strtok()
将 return 指向 char[]
内部的内存指针。因此,每次您从文件中读取新行时,您之前存储在 process[]
数组中的指针仍指向同一内存,但该内存的内容已被更改。
您需要为每个要保存在 process[]
数组中的 name
分配一个单独的 char[]
字符串。您可以为此使用 strdup()
,例如:
while (fgets(string, 150, file)){
char* token1 token1 = strtok(string, " ");
process[process_count].name = strdup(token1); // <-- HERE
...
}
// use process[] as needed...
for(int i = 0; i < process_count; i++){
free(process[i].name);
}
问题是 strtok()
returns 指向它解析的行的指针。因此,process
数组中的所有条目都指向通过调用 fgets()
.
修改的同一个 string
数组
您必须复制存储在流程描述结构中的字符串:
void RoundRobin(const char *filename) {
char string[MAX_SIZE];
Process process[20];
Queue *q = initQueue();
char *token;
FILE *file;
file = fopen(filename, "r");
if (!file) {
printf("Cannot open file %s\n", filename);
return;
}
int time_quantum = 0;
int process_count = 0;
if (fgets(string, sizeof string, file)
&& (token = strtok(string, "=")) != NULL
&& (token = strtok(NULL, "+")) != NULL) {
time_quantum = atoi(token);
}
while (fgets(string, sizeof string, file)) {
char *token1;
if ((token1 = strtok(string, " ")) == NULL)
contine;
process[process_count].name = strdup(token1);
if ((token1 = strtok(string, " ")) == NULL)
contine;
process[process_count].starting_time = atoi(token1);
if ((token1 = strtok(string, " ")) == NULL)
contine;
process[process_count].remaining_time = atoi(token1);
process_count++;
}
for (int i = 0; i < process_count; i++) {
printf("%s %d %d\n", process[i].name, process[i].starting_time, process[i].remaining_time);
}
for (int i = 0; i < process_count; i++) {
free(process[i].name);
}
fclose(file);
}
我正在尝试创建一个程序,该程序从一个文件中获取多个进程(名称、开始时间、剩余时间),然后使用循环算法来处理队列。
问题是,当我尝试使用 strtok()
和 fgets()
对文件的每一行进行标记时,进程名称总是错误的。
例如,如果第一行是 P1 0 3
输出是这样的:
void RoundRobin(char *filename) {
Queue *q = initQueue();
char string[MAX_SIZE];
FILE *file;
Process process[20];
char *token;
file = fopen(filename, "r");
if (!file) {
printf("File Cannot Be Opened");
}
fgets(string, 150, file);
token = strtok(string, "=");
token = strtok(NULL, "+");
int time_quantum = atoi(token);
int process_count = 0;
while (fgets(string, 150, file)) {
char *token1;
token1 = strtok(string, " ");
process[process_count].name = token1;
token1 = strtok(NULL, " ");
process[process_count].starting_time = atoi(token1);
token1 = strtok(NULL, " ");
process[process_count++].remaining_time = atoi(token1);
token1 = strtok(NULL, " ");
}
for (int i = 0; i < process_count; i++) {
printf("%s %d %d\n", process[i].name, process[i].starting_time, process[i].remaining_time);
}
fclose(file);
}
您正在为所有令牌解析重复使用单个 char[]
。 fgets()
每次都会覆盖 char[]
的内容,而 strtok()
将 return 指向 char[]
内部的内存指针。因此,每次您从文件中读取新行时,您之前存储在 process[]
数组中的指针仍指向同一内存,但该内存的内容已被更改。
您需要为每个要保存在 process[]
数组中的 name
分配一个单独的 char[]
字符串。您可以为此使用 strdup()
,例如:
while (fgets(string, 150, file)){
char* token1 token1 = strtok(string, " ");
process[process_count].name = strdup(token1); // <-- HERE
...
}
// use process[] as needed...
for(int i = 0; i < process_count; i++){
free(process[i].name);
}
问题是 strtok()
returns 指向它解析的行的指针。因此,process
数组中的所有条目都指向通过调用 fgets()
.
string
数组
您必须复制存储在流程描述结构中的字符串:
void RoundRobin(const char *filename) {
char string[MAX_SIZE];
Process process[20];
Queue *q = initQueue();
char *token;
FILE *file;
file = fopen(filename, "r");
if (!file) {
printf("Cannot open file %s\n", filename);
return;
}
int time_quantum = 0;
int process_count = 0;
if (fgets(string, sizeof string, file)
&& (token = strtok(string, "=")) != NULL
&& (token = strtok(NULL, "+")) != NULL) {
time_quantum = atoi(token);
}
while (fgets(string, sizeof string, file)) {
char *token1;
if ((token1 = strtok(string, " ")) == NULL)
contine;
process[process_count].name = strdup(token1);
if ((token1 = strtok(string, " ")) == NULL)
contine;
process[process_count].starting_time = atoi(token1);
if ((token1 = strtok(string, " ")) == NULL)
contine;
process[process_count].remaining_time = atoi(token1);
process_count++;
}
for (int i = 0; i < process_count; i++) {
printf("%s %d %d\n", process[i].name, process[i].starting_time, process[i].remaining_time);
}
for (int i = 0; i < process_count; i++) {
free(process[i].name);
}
fclose(file);
}