首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> 關於C語言

C語言 scanf 族函數正則表達式掃描集完整指南

     編輯:關於C語言

掃描集 [%[]] 核心語法

%[chars]:匹配 chars 中任意字符,貪婪讀取直到遇到非集合字符。

%[^chars]:匹配 非 chars 中字符,遇到集合字符停止。

常用模式速查表

格式串匹配內容典型用途
%[a-z]小寫字母讀取單詞
%[a-zA-Z0-9]字母數字讀取標識符
%[^ \n\t]非空白字符讀取一個 token
%[^=]非 '=' 字符解析 key=value
%[^\n]整行 (含空格)讀取一行文本
%*[^=]=%s跳過 key,讀 value提取值部分

實戰範例

1. 讀取一行含空格字符串


char line[100];
scanf("%[^\n]", line);  // 讀到換行符停止,不包含 \n
getchar();  // 吸收殘留的 \n

2. 解析 key=value 格式


char key[32], val[64];
char *s = "username=admin";
sscanf(s, "%[^=]=%s", key, val);
// key="username", val="admin"

3. 跳過不需要的字段


char version[32];
char *s = "app=v1.2.3";
sscanf(s, "%*[^=]=%s", version);
// version="v1.2.3", key 被丟棄

4. 讀取固定寬度


char buf[41];
scanf("%40c", buf);  // 精確讀 40 字符,不加 \0
buf[40] = '\0';      // 手動添加結束符

三大掃描函數對比

函數輸入源適用場景
scanfstdin交互式輸入
fscanfFILE*文件解析
sscanfchar*字符串解析、协议解包

返回值詳解

  • 成功匹配項數:可能少於格式串項數(部分匹配失敗)
  • 0:首項匹配失敗
  • EOF:輸入耗盡或讀取錯誤

陷阱:用 fscanf 判斷文件結束不可靠,匹配失敗返回 0 而非 EOF。應配合 feof() 或檢查實際讀取字節數。

scanf 族函數格式串完整語法

%[*][width][{h|l|ll|L|j|z|t}]type
*       : 抑制賦值 (不存儲)
width   : 最大讀取字符數
h       : short / unsigned short
l       : long / double / wchar_t*
ll      : long long
L       : long double
j       : intmax_t
z       : size_t
t       : ptrdiff_t
type    : d i u o x X f e g a c s p n [...]

常見陷阱與避坑指南

1. 緩衝區溢出
char s[10]; scanf("%s", s); 輸入超過 9 字符會溢出。
修正:scanf("%9s", s); 或用 fgets。
2. 換行符殘留
scanf("%d", &n); scanf("%[^\n]", s); 第二次讀到空行。
修正:中間加 getchar() 或 scanf(" %[^\n]", s) (前導空格吃掉空白)。
3. %c 讀取空白
scanf("%c", &c); 會讀取空格/換行。
修正:scanf(" %c", &c); 前導空格跳過空白。
4. 掃描集不匹配不消耗輸入
scanf("%[0-9]", s); 輸入 "abc" → 返回 0,'a' 留在緩衝區,下次 scanf 仍讀 'a'。
修正:檢查返回值,失敗時手動清理緩衝區。

現代替代方案

  • fgets + sscanf:先整行讀取,再解析,避免緩衝區殘留問題
  • strtok/strsep:簡單分割字符串
  • 正則表達式庫 (PCRE, RE2):複雜模式匹配
  • C++ iostream / stringstream:類型安全、自動內存管理

總結

scanf 掃描集功能強大但易誤用。掌握 %[^chars] 反向匹配、* 抑制賦值、width 防溢出三大技巧,配合 fgets 讀行、sscanf 解析的組合拳,可處理 90% 的文本輸入場景。複雜協議解析建議使用專用解析器生成器 (lex/yacc) 或現代 C++ 庫。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved