linux下getopt函式的用法
getopt()函式用於命令列引數解析。先來看一下main函式的引數。
1,程式引數
C語言編寫的linux程式執行時,是從main函式開始的。main函式的宣告如下:
int main(int argc, char* argv[])
或者
int main(int argc, char** argv)
其中,argc是程式引數的個數,argv是一個代表自身的字串陣列。
實驗:下面這個程式args.c對其引數進行檢查:
<span style="font-size:12px;">#include<stdio.h>
#include<stdlib.h>
int main(int argc, char* argv[])
{
int arg;
printf("The number of parameters: argc=%d\n",argc);
for(arg=0;arg<argc;arg++)
{
printf("argv[%d] = %s\n",arg,argv[arg]);
}
exit(0);
}</span>
經過編譯後,執行
gcc -o args args.c
./args -a -b host -chello -de -f world
結果如下:
The number of parameters: argc=8
argv[0] = ./args
argv[1] = -a
argv[2] = -b
argv[3] = host
argv[4] = -chello
argv[5] = -de
argv[6] = -f
argv[7] = world
注:1)引數個數包括程式名本身; 2)argv是一個字串陣列;3)-de選項其實是-d和-e選項組合的,getopt可以識別這種情況的兩個選項。
2,getopt函式
#include <unistd.h>
int getopt(int argc, char * const argv[], const char *optstring);
以下全域性變數配合 getopt 函式。
extern char *optarg;
extern int optind;
extern int optopt;
extern int opterr;
實際上,在命令列中,可以支援這樣命令輸入的資訊:
選項:一個選項一般完成不同的功能的操作。
引數(關聯值):在執行相應選項功能操作時輸入的資訊。
-a:選項:表示所有。
-h host_id: h 就是一個選項,但host_id 實際上是一個IP,也就是h 的引數。
getopt函式將傳遞給main函式的argc和argv作為引數,同時接受一個選項指定符字串optstring,該字元告訴getopt哪些選項可用,以及它們是否有關聯值(引數)。optstring約定:
(1)如果就是一個字元,表示某個選項。
(2)如果一個字元後有1 個冒號,表示選項後面一定要跟一個引數。引數可以緊跟選項或者與選項相隔一個空格。
(3)如果一個字元後有2 個冒號,表示選項後面可有有一個引數,也可以沒有引數,在選項後的引數一定不能跟它以空格間隔。
例如getopt 函式第三個引數為以下值:
“ab:c::d::”
a 後面 沒有冒號,是一個選項。
b 後面有冒號,其後的內容一定要有理解為引數。
c 和d 雙冒號,其後的內容可以有,也可以沒有,但如果有,則這個引數一定堅挨著。
因此如下:
./getopt –a –b host –chello –d
getopt每次先查詢‘-’後面的字元,再檢視該字元是否是optstring中的選項,以及是否帶有正確的引數。對於前面不帶‘-’的,且不是作為引數的字元或字串,則不予理會。
具體getopt 怎麼來解釋我們的選項和引數。
每成功執行一次,將返回當前的一個選項。迴圈呼叫getopt就可以依次得到每個選項。
(1)如果選項有一個關聯值,則extern char *optarg指向這個值,否則為NULL;
(2)如果選項處理完畢,getopt返回-1;
(3)如果遇到一個無法識別的選項,getopt返回一個問號(?),並把它儲存到外部變數optopt中;並把有一個關聯值,則extern char *optarg指向這個值,否則為NULL;
(4)如果一個選項要求有一個關聯值(例如例子中的-a),但使用者未提供這個值,getopt通常將返回一個問號;但如果
./getopt_exp -a -b 'hi there' -chello world -de -f (optstring為"a:b:c::de")
程式會將-b當成-a的關聯值。
如果我們將選項字串的第一個字元設定為冒號,那麼getopt將在使用者未提供值的情況下返回冒號,而不是?。
extern char *optarg; //如果當前選項後面一定要跟一個引數,且存在引數,則optarg指向該引數;否則為null
extern int optind; //下一個要處理引數的索引
extern int optopt; //用於儲存無法識別的選項
extern int opterr; //opterr== 0,不將錯誤輸出的標準錯誤輸出裝置。
<span style="font-size:12px;">#include<stdio.h>
#include<unistd.h>
int main(int argc, char* argv[])
{
int opt,i;
opterr=0;
while((opt=getopt(argc,argv,"a:b:c::de"))!=-1)
{
switch(opt)
{
case 'a':
printf("option=a,optarg=%s,optind=%d,optopt=%c,opterr=%d\n",optarg,optind,optopt,opterr);
break;
case 'b':
printf("option=b,optarg=%s,optind=%d,optopt=%c,opterr=%d\n",optarg,optind,optopt,opterr);
break;
case 'c':
printf("option=c,optarg=%s,optind=%d,optopt=%c,opterr=%d\n",optarg,optind,optopt,opterr);
break;
case 'd':
printf("option=d,optarg=%s,optind=%d,optopt=%c,opterr=%d\n",optarg,optind,optopt,opterr);
break;
case 'e':
printf("option=e,optarg=%s,optind=%d,optopt=%c,opterr=%d\n",optarg,optind,optopt,opterr);
break;
case '?':
printf("opt=?,optarg=%s,optind=%d,optopt=%c,opterr=%d\n",optarg,optind,optopt,opterr);
break;
default:
printf("default,opt=%c,optarg=%s,optind=%d,optopt=%c,opterr=%d\n",opt,optarg,optind,optopt,opterr);
break;
}
printf("opt=%c\n",opt);
printf("argv[%d]=%s\n",optind,argv[optind]);
}
printf("\nopt=%d,optind=%d\n\n",opt,optind);
for(;optind<argc;optind++)
printf("argv[%d]= %s\n",optind,argv[optind]);
printf("\n");
for(i=1;i<argc;i++)
printf("at the end ---- argv[%d]=%s\n",i,argv[i]);
return 0;
}</span>
編譯:gcc -o getopt_exp getopt_exp.c;執行./getopt_exp -a here -b 'hi there' -chello -de come -f world後,結果為
option=a,optarg=here,optind=3,optopt=,opterr=0
opt=a
argv[3]=-b
option=b,optarg=hi there,optind=5,optopt=,opterr=0
opt=b
argv[5]=-chello
option=c,optarg=hello,optind=6,optopt=,opterr=0
opt=c
argv[6]=-de
option=d,optarg=(null),optind=6,optopt=,opterr=0
opt=d
argv[6]=-de
option=e,optarg=(null),optind=7,optopt=,opterr=0
opt=e
argv[7]=come
opt=?,optarg=(null),optind=9,optopt=f,opterr=0
opt=?
argv[9]=world
opt=-1,optind=8
argv[8]= come
argv[9]= world
at the end ---- argv[1]=-a
at the end ---- argv[2]=here
at the end ---- argv[3]=-b
at the end ---- argv[4]=hi there
at the end ---- argv[5]=-chello
at the end ---- argv[6]=-de
at the end ---- argv[7]=-f
at the end ---- argv[8]=come
at the end ---- argv[9]=world
注:1)getopt能夠處理出現在程式引數中任意位置的選項。程式結束後,getopt實際上重組了argv陣列,把所有非選項引數集中在一起,從argv[optind]位置開始。如程式結果中的argv[8]。
for(;optind<argc;optind++)
printf("argv[%d]= %s\n",optind,argv[optind]);
2)opt,即 getopt函式的返回值,是一個選項,即一個字元,輸出時用%c,不能用%s,否則會出現Segmentation fault (core dumped)的錯誤。
相關文章
- Linux下getopt函式的使用Linux函式
- linux的命令列解析引數之getopt_long函式使用Linux命令列函式
- 1.linux的命令列解析引數之getopt_long函式Linux命令列函式
- Linux-getoptLinux
- linux getopt 命令Linux
- GetModuleFileName函式的用法函式
- Instr函式的用法函式
- string 函式的基本用法函式
- 【Oracle的NVL函式用法】Oracle函式
- abs函式用法函式
- C語言中函式printf()和函式scanf()的用法C語言函式
- StretchBlt函式和BitBlt函式的區別和用法函式
- Excel函式的初級用法Excel函式
- C++ 函式 realloc 的用法C++函式
- Matlab中erf函式的用法Matlab函式
- sys_context函式的用法Context函式
- python中zip()函式的用法Python函式
- PostgreSQL>視窗函式的用法SQL函式
- hive 的函式 lateral view 用法詳解 | 附pdf下載Hive函式View
- SSD-函式用法函式
- Python排序函式用法Python排序函式
- SQL LEN()函式用法SQL函式
- Python range() 函式用法Python函式
- 關於linux下system()函式的總結Linux函式
- Python中的split()函式的用法Python函式
- 分割槽函式Partition By的基本用法函式
- python函式符號sympy的用法Python函式符號
- python sorted()函式的引數用法Python函式
- php array_filter() 函式的用法PHPFilter函式
- C — 快排函式 qsort 的用法函式
- C++中函式呼叫的用法C++函式
- C語言中qsort函式的用法C語言函式
- C語言函式sscanf()的用法C語言函式
- PHP 自定義函式用法及常用函式集合PHP函式
- oracle資料庫常用分析函式與聚合函式的用法Oracle資料庫函式
- C++ replace() 函式用法C++函式
- fcntl函式用法詳解函式
- getopt和getopt_long
- getopt與getopt_long