这是我的结构
typedef struct {
char mmsi[10];
char name[20];
double latitude;
double longitude;
int course;
double speed;
}Vessel;
这是我不想工作的功能
void searchByLatLong(double latitude, double longitude){
FILE * file;
struct dirent *drnt;
DIR * dir = opendir("./text");
char *path = (char *)malloc(19);
Vessel *vessel = (Vessel *)malloc(sizeof(Vessel));
while((drnt = readdir(dir)) != NULL) {
if(strcmp(drnt->d_name,".") && strcmp(drnt->d_name,"..")) {
strcpy(path,"text/");
strcat(path,drnt->d_name);
file=fopen(path, "r");
fscanf(file," %s %[a-zA-Z0-9 ]19s %lf %lf %d %lf", &vessel->mmsi,&vessel->name,&vessel->latitude,&vessel->longitude,&vessel->course,&vessel->speed);
// if (mmsi+".txt" == drnt->d_name){
printf("%s\n%s\n%lf\n%lf\n%d\n%lf\n\n",vessel->mmsi,vessel->name,vessel->latitude,vessel->longitude,vessel->course,vessel->speed);
//}
fclose(file);
}
seekdir(dir, telldir(dir));
// if(this->mmsi == mmsi){
// printVessel();
// }
}
closedir(dir);
}
当我尝试加载txt文件时,它只加载两个第一个字符串,然后加载内存中的一些垃圾。将数据加载到另一个变量没有任何改变; / 这是一个应加载的示例txt文件:
3
RMS Titanic
22.222
33.333
4
5.9
答案 0 :(得分:2)
问题出在你的格式字符串上。正确的格式字符串是:
" %s %19[a-zA-Z0-9 ] %lf %lf %d %lf"
字段宽度在转换说明符之前。此外,[...]序列是一个转换说明符,就像's'一样。您看到的问题是fscanf()
处理'3',因为它与第一个%s
匹配。然后它处理'RMS Titanic',因为它匹配%[a-zA-Z0-9 ]
,但随后处理停止,因为输入中没有'19s'。此时剩下的参数都是未初始化的。
您应该检查fscanf()
的返回值。它会告诉你实际执行了多少次转换。
答案 1 :(得分:0)
感谢您发布一个有趣的问题;我了解了fscanf()
和它接受的[]
符号。
[]
表示法指定正在读取字符串,因此,您附加到其上的s
被视为应匹配的文字字符。同样,您提供的宽度说明符19
应出现在[]
之前。
如果您有一艘名为“RMS Titanic19s”的船,您当前的代码将开始工作。
将您的fscanf更改为:
fscanf(file," %s %19[a-zA-Z0-9 ] %lf %lf %d %lf",
vessel->mmsi,vessel->name,&vessel->latitude,
&vessel->longitude,&vessel->course,&vessel->speed);
您的代码将开始工作。
注意我通过从&
成员char []
和mmsi
中删除多余的name
来修复了一些编译警告 - 这些警告已指向您要填充的缓冲区。您前面不需要&
。教学替代形式是&vessel->mmsi[0]
- mmsi
的第一个字符的地址。