我正在尝试使用带有分隔符"" 的strtok函数来解析GNRMC字符串,当我注意到一些我不期待的不同时,一切都很顺利。 如果String包含连续的" ,," ,那么strtok过冲和打印功能错误地放置了真实数据,我的目标是在那里&#39时打印数字 0 ;在连续" ,,"
之间没有数据可用我该怎么做??
这是我的代码
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main()
{
char str[] = "$GPRMC,105954.000,A,3150.6731,N,11711.9399,E,0.00,96.10,250313,,,A*53";
char* Message_ID = strtok(str,",");
char* Time = strtok(NULL,",");
char* Data_Valid = strtok(NULL,",");
char* Raw_Latitude = strtok(NULL,",");
char* N_S = strtok(NULL,",");
char* Raw_Longitude = strtok(NULL,",");
char* E_W = strtok(NULL,",");
char* Speed = strtok(NULL,",");
char* COG = strtok(NULL,",");
char* Date = strtok(NULL,",");
char* Magnetic_Variation = strtok(NULL,",");
char* M_E_W = strtok(NULL,",");
char* Positioning_Mode = strtok(NULL,",");
double Latitude = atof(Raw_Latitude);
double Longitude = atof(Raw_Longitude);
printf("The Message ID is : %s\n", Message_ID);
printf("The Time is : %s\n", Time);
printf("The data valid is : %s\n", Data_Valid);
printf("The Latitude is : %f\n", Latitude);
printf("The N_S is : %s\n", N_S);
printf("The Longitude is : %f\n", Longitude);
printf("The E_W is : %s\n", E_W);
printf("The Speed is : %s\n", Speed);
printf("The COG is : %s\n", COG);
printf("The Date is : %s\n", Date);
printf("The Magnetic_Variation is : %s\n", Magnetic_Variation);
printf("The M_E_W is : %s\n", M_E_W);
printf("The Positioning_Mode is : %s\n", Positioning_Mode);
return 0;
}
答案 0 :(得分:2)
如果您仅检测到一个特定字符(例如','
),那么直接的方法就是使用旧的strchr()
。
char str[] =
"$GPRMC,105954.000,A,3150.6731,N,11711.9399,E,0.00,96.10,250313,,,A*53";
char* message_id = str;
char* time = strchr(message_id, ','); *time = '\0'; ++time;
char* data_valid = strchr(time,","); *data_valid = '\0'; ++data_valid;
char* raw_latitude = strchr(data_valid,","); *raw_latitude = '\0'; ++raw_latitude;
...
棘手的宏可以简化使用:
#define FIND_AND_NUL(s, p, c) ( \
(p) = strchr(s, c), \
*(p) = '\0', \
++(p), \
(p))
像这样使用:
char str[] =
"$GPRMC,105954.000,A,3150.6731,N,11711.9399,E,0.00,96.10,250313,,,A*53";
char* message_id = str;
char* time = FIND_AND_NUL(message_id, time, ',');
char* data_valid = FIND_AND_NUL(time, data_valid, ',');
char* raw_latitude = FIND_AND_NUL(data_valid, raw_latitude, ',');
...
答案 1 :(得分:1)
我使用自己的strtok函数,该函数非常简单,但与原始函数有两个区别:(1) 如果要解析的字符串具有两个连续的定界符,则定界符仅是单个字符,而不是字符串(2),该函数将返回一个空的非NULL标记“”。这对于解析NMEA消息非常方便。
char *strtok_fr (char *s, char delim, char **save_ptr)
{
char *tail;
char c;
if (s == NULL) {
s = *save_ptr;
}
tail = s;
if ((c = *tail) == '\0') {
s = NULL;
}
else {
do {
if (c == delim) {
*tail++ = '\0';
break;
}
}while ((c = *++tail) != '\0');
}
*save_ptr = tail;
return s;
}
非递归版本:
char *strtok_f (char *s, char delim)
{
static char *save_ptr;
return strtok_fr (s, delim, &save_ptr);
}
因此,您的示例(请注意用','代替“,”分隔符,并用strtok_f代替strtok函数):
int main (int argc, char *argv[])
{
char str[] = "$GPRMC,105954.000,A,3150.6731,N,11711.9399,E,0.00,96.10,250313,,,A*53";
char* Message_ID = strtok_f(str,',');
char* Time = strtok_f(NULL,',');
char* Data_Valid = strtok_f(NULL,',');
char* Raw_Latitude = strtok_f(NULL,',');
char* N_S = strtok_f(NULL,',');
char* Raw_Longitude = strtok_f(NULL,',');
char* E_W = strtok_f(NULL,',');
char* Speed = strtok_f(NULL,',');
char* COG = strtok_f(NULL,',');
char* Date = strtok_f(NULL,',');
char* Magnetic_Variation = strtok_f(NULL,',');
char* M_E_W = strtok_f(NULL,',');
char* Positioning_Mode = strtok_f(NULL,',');
double Latitude = atof(Raw_Latitude);
double Longitude = atof(Raw_Longitude);
printf("The Message ID is : %s\n", Message_ID);
printf("The Time is : %s\n", Time);
printf("The data valid is : %s\n", Data_Valid);
printf("The Latitude is : %f\n", Latitude);
printf("The N_S is : %s\n", N_S);
printf("The Longitude is : %f\n", Longitude);
printf("The E_W is : %s\n", E_W);
printf("The Speed is : %s\n", Speed);
printf("The COG is : %s\n", COG);
printf("The Date is : %s\n", Date);
printf("The Magnetic_Variation is : %s\n", Magnetic_Variation);
printf("The M_E_W is : %s\n", M_E_W);
printf("The Positioning_Mode is : %s\n", Positioning_Mode);
return 0;
}
现在的结果:
消息ID为:$ GPRMC
时间是:105954.000
有效数据为:A
纬度为:3150.673100
N_S是:N
经度是:11711.939900
E_W是:E
速度为:0.00
COG为:96.10
日期是:250313
Magnetic_Variation为:
M_E_W是:
Positioning_Mode为:A * 53
C:\ Users \ froca \ Desktop \ strtok>
请注意,“磁变”和“ M_E_W”现在是空标记。那是关键。