You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C语言中从字符串提取并格式化时钟小时和分钟变量问题

问题描述

我使用一个返回char*类型的库函数,它返回调制解调器的日期字符串,格式为"+QLTS: \"2022/11/16,09:51:56+32,0\""。我想通过strtok提取小时和分钟,存储为int类型变量t_hour和t_min(后续会设为全局变量)。24小时制的令牌能正常获取,但处理"09"这类带前导0的格式转成数字9时,遇到了字符串类型转换的编译错误,附上尝试的代码:

char * time_buffer = (char *)fona.getTime();
char hour_tok[2];
char min_tok[2];
int t_hour;
int t_min;
    
if (strcmp(time_buffer, "ERROR") != 0) // 
{   
    strtok(time_buffer, ",");
    hour_tok = strtok(NULL, ",");  
        
    strtok(hour_tok, ":"); 
    min_tok = strtok(NULL, ":"); 
    
    if(hour_tok[0] == "0")
    {
     t_hour = atoi(hour_tok[1]);
    }
    else
    {
        t_hour = atoi(hour_tok);
    }
    
    
    if(min_tok[0] == "0")
    {
     t_min = atoi(min_tok[1]);
    }
    else
    {
        t_min = atoi(min_tok);
    }

    Serial.println(F("<<<<<TIME HR>>>>>"));
    Serial.println(String(t_hour));
    Serial.println(F("<<<<<TIME MIN>>>>>"));
    Serial.println(String(t_min));
}
代码中的错误点
  • 数组不能直接赋值:hour_tok = strtok(NULL, ","); 这类写法错误,数组名是常量指针,不能作为左值赋值,需用strcpy复制字符串内容。
  • 字符与字符串比较错误:hour_tok[0] == "0" 中,"0"是字符串常量,hour_tok[0]是单个字符,应该用单引号包裹字符:hour_tok[0] == '0'。
  • atoi参数类型错误:atoi(hour_tok[1]) 传递的是单个字符,而atoi需要的是字符串指针,正确写法是atoi(&hour_tok[1]),或者直接用字符减'0'转数字。
  • 数组长度不足:hour_tok[2]无法容纳"09"这类2字符的字符串,C字符串需要末尾的\0结束符,所以数组至少要定义为char hour_tok[3];。
修正后的代码

方法1:保留前导0判断逻辑

char * time_buffer = (char *)fona.getTime();
// 定义足够长度的数组,容纳2字符+结束符
char hour_tok[3];
char min_tok[3];
int t_hour;
int t_min;

if (strcmp(time_buffer, "ERROR") != 0)
{   
    // 跳过日期部分,获取时间段字符串
    strtok(time_buffer, ",");
    char* time_segment = strtok(NULL, ",");  
    
    // 分割时间字符串,提取小时
    strtok(time_segment, ":"); 
    strcpy(hour_tok, strtok(NULL, ":")); 
    // 提取分钟
    strcpy(min_tok, strtok(NULL, ":")); 

    // 处理小时前导0
    if(hour_tok[0] == '0')
    {
        // 字符转数字,等价于atoi(&hour_tok[1])
        t_hour = hour_tok[1] - '0';
    }
    else
    {
        t_hour = atoi(hour_tok);
    }
    
    // 处理分钟前导0
    if(min_tok[0] == '0')
    {
        t_min = min_tok[1] - '0';
    }
    else
    {
        t_min = atoi(min_tok);
    }

    Serial.println(F("<<<<<TIME HR>>>>>"));
    Serial.println(String(t_hour));
    Serial.println(F("<<<<<TIME MIN>>>>>"));
    Serial.println(String(t_min));
}

方法2:利用atoi自动处理前导0(更简洁)

其实atoi会自动忽略前导0,直接将"09"转换为9,所以可以省去前导0的判断逻辑:

char * time_buffer = (char *)fona.getTime();
int t_hour;
int t_min;

if (strcmp(time_buffer, "ERROR") != 0)
{   
    // 跳过日期部分
    strtok(time_buffer, ",");
    char* time_segment = strtok(NULL, ",");  
    
    // 直接分割提取小时和分钟字符串
    char* hour_str = strtok(time_segment, ":"); 
    char* min_str = strtok(NULL, ":"); 

    // atoi自动处理前导0,直接转成int
    t_hour = atoi(hour_str);
    t_min = atoi(min_str);

    Serial.println(F("<<<<<TIME HR>>>>>"));
    Serial.println(String(t_hour));
    Serial.println(F("<<<<<TIME MIN>>>>>"));
    Serial.println(String(t_min));
}

内容的提问来源于stack exchange,提问作者Tyranus

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.12 20:30:39