GNU/Linux >> Tutoriels Linux >  >> Linux

C argc et argv Exemples d'analyse d'arguments de ligne de commande

Chaque fois que vous exécutez un programme sur un terminal, vous pouvez passer des arguments attendus par le programme, qui peuvent être utilisés lors de l'exécution du programme. Ici, le système fournit une installation interne pour conserver tous les arguments transmis par l'utilisateur lors de l'exécution du programme. Ces arguments sont appelés "arguments de ligne de commande".

Dans ce didacticiel, nous allons mapper la compréhension des arguments de ligne de commande avec le programme de travail pour mieux le comprendre de manière claire et nette. Mais avant de passer au programme, nous devons savoir comment le système fournit la possibilité d'arguments de ligne de commande. Comme nous le savons, chaque programme C doit avoir la fonction main() et la fonction d'arguments de ligne de commande est fournie par la fonction main() elle-même. Lorsqu'elle est donnée ci-dessous, la déclaration est utilisée dans le programme, puis le programme a la possibilité d'utiliser/de manipuler les arguments de la ligne de commande.

int main (int argc, char *argv[])

Ici, le paramètre argc est le nombre total d'arguments de ligne de commande passés à l'exécutable lors de l'exécution (y compris le nom de l'exécutable comme premier argument). Le paramètre argv est le tableau de la chaîne de caractères de chaque argument de ligne de commande transmis à l'exécutable lors de l'exécution. Si vous débutez dans la programmation C, vous devez d'abord comprendre le fonctionnement du tableau C.

Vous trouverez ci-dessous le programme de travail utilisant l'argument de ligne de commande.

 #include <stdio.h>

 int main (int argc, char *argv[]) {
 int i=0;
 printf("\ncmdline args count=%s", argc);

 /* First argument is executable name only */
 printf("\nexe name=%s", argv[0]);

 for (i=1; i< argc; i++) {
     printf("\narg%d=%s", i, argv[i]);
 }

 printf("\n");
 return 0;
 }

Ci-dessous est la sortie lorsque le programme est exécuté.

$ ./cmdline_basic test1 test2 test3 test4 1234 56789
cmdline args count=7
 exe name=./cmdline_basic
 arg1=test1
 arg2=test2
 arg3=test3
 arg4=test4
 arg5=1234
 arg6=56789

Dans la sortie ci-dessus, nous pouvons voir que le nombre total d'arguments est géré en interne par le paramètre "argc" de main() qui contient la valeur '7' (dans laquelle un argument est le nom de l'exécutable et '6' sont des arguments passés au programme). les valeurs des arguments sont stockées dans le paramètre « argv » de main() qui est un tableau de chaînes de caractères. Ici, la fonction main () stocke chaque valeur d'argument sous forme de chaîne de caractères. Nous pouvons voir qu'en itérant sur le tableau "argv", nous pouvons obtenir tous les arguments passés dans le programme.

Il existe une autre déclaration de la fonction main () qui fournit une facilité supplémentaire pour travailler sur les variables d'environnement à l'intérieur du programme. Comme les arguments maintenus dans le tableau argv[], la fonction main() a une fonction interne pour maintenir toutes les variables d'environnement système dans un tableau de chaînes de caractères qui peuvent être prises comme paramètre de la fonction main(). Ci-dessous la déclaration.

int main (int argc, char *argv[], char **envp)

Vous trouverez ci-dessous le programme de travail utilisant un argument de ligne de commande avec des variables d'environnement.

#include <stdio.h>

int main (int argc, char *argv[], char **env_var_ptr) {
int i=0;
printf("\ncmdline args count=%d", argc);

/* First argument is executable name only */
printf("\nexe name=%s", argv[0]);

for (i=1; i< argc; i++) {
   printf("\narg%d=%s", i, argv[i]);
 }

i=0;
while (*env_var_ptr != NULL) {
    i++;
    printf ("\nenv var%d=>%s",i, *(env_var_ptr++));
 }

printf("\n");
return 0;
}

La sortie du programme ci-dessus est donnée ci-dessous.

$ ./env test1 test2
cmdline args count=3
 exe name=./env
 arg1=test1
 arg2=test2
 env var1=>SSH_AGENT_PID=1575
 env var2=>KDE_MULTIHEAD=false
 env var3=>SHELL=/bin/bash
 env var4=>TERM=xterm
 env var5=>XDG_SESSION_COOKIE=5edf27907e97deafc70d310550995c84-1352614770.691861-1384749481
 env var6=>GTK2_RC_FILES=/etc/gtk-2.0/gtkrc:/home/sitaram/.gtkrc-2.0:/home/sitaram/.kde/share/config/gtkrc-2.0
 env var7=>KONSOLE_DBUS_SERVICE=:1.76
 env var8=>KONSOLE_PROFILE_NAME=Shell
 env var9=>GS_LIB=/home/sitaram/.fonts
 env var10=>GTK_RC_FILES=/etc/gtk/gtkrc:/home/sitaram/.gtkrc:/home/sitaram/.kde/share/config/gtkrc
 env var11=>WINDOWID=29360154
 env var12=>GNOME_KEYRING_CONTROL=/run/user/sitaram/keyring-2Qx7DW
 env var13=>SHELL_SESSION_ID=f7ac2d9459c74000b6fd9b2df1d48da4
 env var14=>GTK_MODULES=overlay-scrollbar
 env var15=>KDE_FULL_SESSION=true
 env var16=>http_proxy=http://10.0.0.17:8080/
 env var17=>USER=sitaram
 env var18=>LS_COLORS=rs=0:di=01;34:ln=01;36:mh=00:pi=40;33:so=01;35:do=01;35:bd=40;33;01:cd=40;33;01:or=40;31;01:su=37;41:sg=30;43:ca=30;41:tw=30;42:ow=34;42:st=37;44:ex=01;32:*.tar=01;31:*.tgz=01;31:*.arj=01;31:*.taz=01;31:*.lzh=01;31:*.lzma=01;31:*.tlz=01;31:*.txz=01;31:*.zip=01;31:*.z=01;31:*.Z=01;31:*.dz=01;31:*.gz=01;31:*.lz=01;31:*.xz=01;31:*.bz2=01;31:*.bz=01;31:*.tbz=01;31:*.tbz2=01;31:*.tz=01;31:*.deb=01;31:*.rpm=01;31:*.jar=01;31:*.war=01;31:*.ear=01;31:*.sar=01;31:*.rar=01;31:*.ace=01;31:*.zoo=01;31:*.cpio=01;31:*.7z=01;31:*.rz=01;31:*.jpg=01;35:*.jpeg=01;35:*.gif=01;35:*.bmp=01;35:*.pbm=01;35:*.pgm=01;35:*.ppm=01;35:*.tga=01;35:*.xbm=01;35:*.xpm=01;35:*.tif=01;35:*.tiff=01;35:*.png=01;35:*.svg=01;35:*.svgz=01;35:*.mng=01;35:*.pcx=01;35:*.mov=01;35:*.mpg=01;35:*.mpeg=01;35:*.m2v=01;35:*.mkv=01;35:*.webm=01;35:*.ogm=01;35:*.mp4=01;35:*.m4v=01;35:*.mp4v=01;35:*.vob=01;35:*.qt=01;35:*.nuv=01;35:*.wmv=01;35:*.asf=01;35:*.rm=01;35:*.rmvb=01;35:*.flc=01;35:*.avi=01;35:*.fli=01;35:*.flv=01;35:*.gl=01;35:*.dl=01;35:*.xcf=01;35:*.xwd=01;35:*.yuv=01;35:*.cgm=01;35:*.emf=01;35:*.axv=01;35:*.anx=01;35:*.ogv=01;35:*.ogx=01;35:*.aac=00;36:*.au=00;36:*.flac=00;36:*.mid=00;36:*.midi=00;36:*.mka=00;36:*.mp3=00;36:*.mpc=00;36:*.ogg=00;36:*.ra=00;36:*.wav=00;36:*.axa=00;36:*.oga=00;36:*.spx=00;36:*.xspf=00;36:
 env var19=>XDG_SESSION_PATH=/org/freedesktop/DisplayManager/Session0
 env var20=>XDG_SEAT_PATH=/org/freedesktop/DisplayManager/Seat0
 env var21=>SSH_AUTH_SOCK=/tmp/ssh-kIFY5HttOJxe/agent.1489
 env var22=>ftp_proxy=ftp://10.0.0.17:8080/
 env var23=>SESSION_MANAGER=local/Sitaram:@/tmp/.ICE-unix/1716,unix/Sitaram:/tmp/.ICE-unix/1716
 env var24=>DEFAULTS_PATH=/usr/share/gconf/kde-plasma.default.path
 env var25=>XDG_CONFIG_DIRS=/etc/xdg/xdg-kde-plasma:/etc/xdg
 env var26=>DESKTOP_SESSION=kde-plasma
 env var27=>PATH=/usr/lib/lightdm/lightdm:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games
 env var28=>PWD=/home/sitaram/test_progs/cmdline
 env var29=>socks_proxy=socks://10.0.0.17:8080/
 env var30=>KONSOLE_DBUS_WINDOW=/Windows/1
 env var31=>KDE_SESSION_UID=1000
 env var32=>LANG=en_IN
 env var33=>GNOME_KEYRING_PID=1478
 env var34=>MANDATORY_PATH=/usr/share/gconf/kde-plasma.mandatory.path
 env var35=>UBUNTU_MENUPROXY=libappmenu.so
 env var36=>KONSOLE_DBUS_SESSION=/Sessions/1
 env var37=>https_proxy=https://10.0.0.17:8080/
 env var38=>GDMSESSION=kde-plasma
 env var39=>SHLVL=1
 env var40=>HOME=/home/sitaram
 env var41=>COLORFGBG=15;0
 env var42=>KDE_SESSION_VERSION=4
 env var43=>LANGUAGE=en_IN:en
 env var44=>XCURSOR_THEME=Oxygen_White
 env var45=>LOGNAME=sitaram
 env var46=>XDG_DATA_DIRS=/usr/share/kde-plasma:/usr/local/share/:/usr/share/
 env var47=>DBUS_SESSION_BUS_ADDRESS=unix:abstract=/tmp/dbus-mnJhMvd4jG,guid=435ddd41500fd6c5550ed8d2509f4374
 env var48=>LESSOPEN=| /usr/bin/lesspipe %s
 env var49=>PROFILEHOME=
 env var50=>XDG_RUNTIME_DIR=/run/user/sitaram
 env var51=>DISPLAY=:0
 env var52=>QT_PLUGIN_PATH=/home/sitaram/.kde/lib/kde4/plugins/:/usr/lib/kde4/plugins/
 env var53=>LESSCLOSE=/usr/bin/lesspipe %s %s
 env var54=>XAUTHORITY=/tmp/kde-sitaram/xauth-1000-_0
 env var55=>_=./env
 env var56=>OLDPWD=/home/sitaram/test_progs
$

Dans la sortie ci-dessus, nous pouvons voir que toutes les variables d'environnement système peuvent être obtenues en troisième paramètre de la fonction main() qui sont parcourues dans le programme et affichées dans la sortie.

Passer des arguments de ligne de commande pour programmer et manipuler des arguments

Le programme ci-dessous fonctionne sur les arguments de la ligne de commande.

#include <stdio.h>
#include <stdlib.h>

int main (int argc, char *argv[]) {
int i=0;
int d;
float f;
long int l;
FILE *file = NULL;
printf("\ncmdline args count=%d", argc);

/* First argument is executable name only */
printf("\nexe name=%s", argv[0]);

for (i=1; i< argc; i++) {
    printf("\narg%d=%s", i, argv[i]);
 }

/* Conversion string into int */
d = atoi(argv[1]);
printf("\nargv[1] in intger=%d",d);

/* Conversion string into float */
f = atof(argv[1]);
printf("\nargv[1] in float=%f",f);

/* Conversion string into long int */
l = strtol(argv[2], NULL, 0);
printf("\nargv[2] in long int=%ld",l);

/*Open file whose path is passed as an argument */
file = fopen( argv[3], "r" );

/* fopen returns NULL pointer on failure */
if ( file == NULL) {
    printf("\nCould not open file");
  }
else {
    printf("\nFile (%s) opened", argv[3]);
    /* Closing file */
    fclose(file);
  }

printf("\n");
return 0;
}

La sortie du programme ci-dessus est donnée ci-dessous.

 $ ./cmdline_strfunc 1234test 12345678 /home/sitaram/test_progs/cmdline/cmdline_strfunc.c
cmdline args count=4
 exe name=./cmdline_strfunc
 arg1=1234test
 arg2=12345678
 arg3=/home/sitaram/test_progs/cmdline/cmdline_strfunc.c
 argv[1] in intger=1234
 argv[1] in float=1234.000000
 argv[2] in long int=12345678
 File (/home/sitaram/test_progs/cmdline/cmdline_strfunc.c) opened

Dans la sortie ci-dessus, nous pouvons voir que les arguments de la ligne de commande peuvent être manipulés dans le programme ; tous les arguments sont obtenus sous forme de chaîne de caractères qui peut être convertie en nombre entier, flottant, long comme indiqué dans le programme. Même n'importe quelle chaîne de caractères est transmise comme chemin d'accès à n'importe quel fichier pouvant être utilisé par le programme pour effectuer une opération de gestion de fichiers sur ce fichier. Nous pouvons voir dans le programme ci-dessus, (/home/sitaram/test_progs/cmdline/cmdline_strfunc.c ) le chemin du fichier est passé comme argument de ligne de commande qui est utilisé dans le programme pour ouvrir le fichier et le fermer.

API Getopt()

Si nous explorons davantage les arguments de ligne de commande, nous avons une API très puissante - getopt(). Il facilite au programmeur l'analyse des options de ligne de commande. Le programmeur peut donner la liste des options de ligne de commande obligatoires ou facultatives à getopt(). Il peut déterminer si l'option de ligne de commande est valide ou invalide selon les options de ligne de commande attendues du programme. Il existe peu de variables internes spécifiques à getopt() comme "optarg, optopt, opterr"

  • Optarg :contient un pointeur vers l'argument de l'option valide de la ligne de commande
  • Désactiver :contient l'option de ligne de commande si l'option de ligne de commande obligatoire est manquante
  • Opterr  :défini sur différent de zéro lorsqu'une option non valide est fournie ou que la valeur de l'option de ligne de commande obligatoire n'est pas donnée

Vous trouverez ci-dessous un programme de base pour comprendre l'analyse des options de ligne de commande.

#include <stdio.h>
#include <unistd.h>

int main (int argc, char *argv[]) {
int opt = 0;
char *in_fname = NULL;
char *out_fname = NULL;

while ((opt = getopt(argc, argv, "i:o:")) != -1) {
    switch(opt) {
    case 'i':
    in_fname = optarg;
    printf("\nInput option value=%s", in_fname);
    break;
    case 'o':
    out_fname = optarg;
    printf("\nOutput option value=%s", out_fname);
    break;
    case '?':
    /* Case when user enters the command as
     * $ ./cmd_exe -i
     */
    if (optopt == 'i') {
    printf("\nMissing mandatory input option");
    /* Case when user enters the command as
     * # ./cmd_exe -o
     */
  } else if (optopt == 'o') {
     printf("\nMissing mandatory output option");
  } else {
     printf("\nInvalid option received");
  }
  break;
 }
 }

printf("\n");
return 0;
 }

La sortie du programme ci-dessus est donnée ci-dessous avec quelques combinaisons d'options de ligne de commande :

Case1:
$ ./cmdline_getopt -i /tmp/input -o /tmp/output
Input option value=/tmp/input
 Output option value=/tmp/output

Case2:
$ ./cmdline_getopt -i -o /tmp/output
Input option value=-o

Case3:
$ ./cmdline_getopt -i
 ./cmdline_getopt: option requires an argument -- 'i'
Missing mandatory input option

Case4:
$ ./cmdline_getopt -i /tmp/input -o
./cmdline_getopt: option requires an argument -- 'o'
 Input option value=/tmp/input
 Missing mandatory output option

Case5:
$ ./cmdline_getopt -k /tmp/input
 ./cmdline_getopt: invalid option -- 'k'
Invalid option received

Dans le programme ci-dessus, 'i' et 'o' sont considérés comme des options de ligne de commande d'entrée et de sortie obligatoires pour le programme utilisant l'API getopt().

Nous aurions maintenant une explication de base de chaque cas exécuté dans le programme ci-dessus :

  • Dans le cas 1, les deux options de ligne de commande obligatoires avec leurs arguments sont fournies et sont correctement gérées dans les deux premiers cas de condition de changement de programme.
  • Dans le cas 2, la valeur de l'option d'entrée obligatoire n'est pas donnée, mais nous pouvons voir que getopt() n'est pas assez intelligent et considère "-o" comme valeur de l'option de ligne de commande "I". Ce n'est pas un cas d'erreur pour getopt(), mais le programmeur peut lui-même ajouter de l'intelligence pour gérer ce cas.
  • Dans le cas 3, seule l'option de ligne de commande est spécifiée sans sa valeur et il s'agit d'une option obligatoire. Dans ce cas, getopt() renverrait '?' et la variable "optopt" est définie sur 'i' pour confirmer que la valeur de l'option d'entrée obligatoire est manquant.
  • Dans Case4, la valeur de l'option de sortie obligatoire est manquante.
  • Dans le cas 5, une option de ligne de commande non valide est donnée, ce qui n'est pas une option de ligne de commande obligatoire ou facultative. Dans ce cas, getopt() a renvoyé '?' et optopt n'est pas défini car il s'agit d'un caractère inconnu non attendu par getopt().

Linux
  1. Commande Linux Cat :utilisation et exemples

  2. La commande Linux Sed :utilisation et exemples

  3. Tutoriel sur les commandes Linux nice et renice (7 exemples)

  4. Commandes Linux - Présentation et exemples

  5. Passer les arguments de la ligne de commande au script Bash ?

Commande Diff sous Linux avec exemples

Options de commande et exemples de commande Tee sous Linux

50 exemples simples et utiles de la commande Find sous Linux

16 exemples pratiques et utiles de la commande Echo sous Linux

19 trucs et astuces utiles pour la ligne de commande Linux

Arguments Pycharm et sys.argv