我在一些文本的最后输出了一个垃圾字符:
hum 1345342342 ~Users/Documents ecabd459 //line that was read in from stdin
event action: hum_?
event timestamp: 1345342342
event path: ~Users/Documents
event hash: ecabd459
在事件操作值结束时有一个'_?'输出的垃圾字符。这可以通过将变量的最后位置设置为空终止符(event.action[3] = '\0'
)来纠正,这一切都很好,但是我很困惑的另一个char数组event.hash
没有表现出这种类型行为我以相同的方式创建/打印它们,但哈希行为不一样。
注意:我正在考虑这可能是因为哈希值严格遵循换行符(我顺便说一句),所以我测试了我的程序并重新排序输入无效(也就是说,在哈希值在线上的位置后添加了一个额外的空格和单词)。
相关代码如下:
struct Event{
char action[4];
long timestamp;
char* path;
char hash[9];
};
// parse line and return an Event struct
struct Event parseLineIntoEvent(char* line) {
struct Event event;
char* lineSegment;
int i = 0;
lineSegment = strtok(line, " ");
while (lineSegment != NULL) {
if (i > 3) {
printf("WARNING: input format error!\n");
break;
}
if (i == 0)
strncpy(event.action, lineSegment, sizeof(event.action)-1);
else if(i == 1)
event.timestamp = atoi(lineSegment);
else if(i == 2) {
event.path = malloc(sizeof(lineSegment));
strcpy(event.path, lineSegment);
} else if(i == 3)
strncpy(event.hash, lineSegment, sizeof(event.hash)-1);
lineSegment = strtok(NULL, " ");
i++;
} // while
return event;
} // parseLineIntoEvent()
int main (int argc, const char * argv[]) {
//...
printf("%s\n",line); //prints original line that was read in from stdin
struct Event event = parseLineIntoEvent(line);
printf("event action: %s\n", event.action);
printf("event timestamp: %lu\n", event.timestamp);
printf("event path: %s\n", event.path);
printf("event hash: %s\n", event.hash);
free(event.path);
free(line);
//...
return 0;
}
修改 我用这个函数读了一行,它删除了换行符:
// read in line from stdin, eliminating newline character if present
char* getLineFromStdin() {
char *text;
int textSize = 50*sizeof(char);
text = malloc(textSize);
if ( fgets(text, textSize, stdin) != NULL ) {
char *newline = strchr(text, '\n'); // search for newline character
if ( newline != NULL ) {
*newline = '\0'; // overwrite trailing newline
}
}
return text;
}
提前致谢!
答案 0 :(得分:3)
这是一个错误:
event.path = malloc(sizeof(lineSegment));
将返回sizeof(char*)
,当您需要长度加1来终止NULL字符时:
event.path = malloc(sizeof(char) * (strlen(lineSegment) + 1));
为避免必须将空字符串终止符插入action
和hash
,您可以初始化event
:
struct Event event = { 0 };
答案 1 :(得分:2)
The strncpy() function is similar, except that at most n bytes of src are copied. Warning: If there is no null byte among the first n bytes of src, the string placed in dest will not be null-terminated.
执行strncpy
时,您必须确保目标字符串已正确终止。
更改event.action
字段的设置:
if (i == 0)
{
strncpy(event.action, lineSegment, sizeof(event.action)-1);
event.action[sizeof(event.action)-1] = '\0';
}
答案 2 :(得分:1)
你不走运。 hash [8]可能通过纯粹的(坏)运气获得了'\ 0'。但是我对另一个char数组event.hash没有表现出这种行为的事实感到困惑
尝试在strtok循环之前将其设置为“随机”
int i = 0;
event.hash[8] = '_'; /* forcing good-luck */
lineSegment = strtok(line, " ");
while (lineSegment != NULL) {
答案 3 :(得分:0)
这是因为,字符串“num”只接受来自4个元素字符数组Event.action的三个元素,第四个元素将保持未设置状态。因为没有为Event.action数组元素设置任何内容,所以它将指向存储了一些随机值的随机内存位置。当你打印这个字符数组时,它将打印所有元素而不是那些指向有效数据的元素。这会导致垃圾字符出现。