Précédent Remonter Suivant

2.2  Introduction aux variables, aux types simples et aux instructions

2.2.1  Identificateurs en C




Exercice 2.2 --- Identificateurs.


Le programme suivant tente de définir des variables locales de type entier :
int main(void){

  int 
    nom1, 1nom, nom_2, nom.2, _nom_3, -nom-3, Nom_de_variable, 
    Nom de variable, deuxieme_choix, deuxième_choix, mot_francais,
    mot_français, fonction-1, _MOYENNE_du_MOIS_, 3e_jour, limite_inf.,
    lim_supérieure, __A_, _, a, 3 ;
}
Malheureusement, certains identificateurs ne sont pas licites. Corriger ce programme en modifiant les identificateurs qui ne devraient pas être utilisés (expliciter à chaque fois l'erreur commise).


2.2.2  Variables et types des variables

Schématiquement, une variable correspond à un emplacement en mémoire contenant une information. Dans le code source, cette information est manipulée par l'entremise du nom de la variable.

Le C est un langage typé. Toute variable, constante ou fonction doit être d'un type précis. Le type d'un objet définit la façon dont il est représenté en mémoire et les manipulations qu'on peut faire avec lui.

La norme ANSI spécifie les types et les opérations sur les variables suivants : Ainsi, on définit un caractère par l'instruction : char nom; et on peut lui affecter le caractère A par l'instruction nom='A';.

On peut définir une variable foo stockant la chaîne de caractères bar par l'instruction char *foo="bar";.

De même, on définit un entier et un flottant grâce aux instructions int nom=666; et float nom=3.14;.

Le programme --- erroné --- suivant devrait afficher le résultat de la multiplication de 1500 par 6,55957.
   #include "stdio.h"

   int main(void) {
          int  A ;
          int  B ;
          float  R   ;

          A = 1500    ;
          B = 6.55957 ;
          R = A*B     ;
         // pour l'affichage 
         printf("Le resultat de la multiplication est %f\n",R) ;

         return 1 ;
  }
Ce programme compile mais le résultat est erroné. En effet, l'affectation effectue une conversion de type implicite : quand c'est possible l'expression de droite est convertie dans le type du terme de gauche.




Exercice 2.3 --- Correction d'un programme.


Corriger le programme.
Indication :
pensez à afficher le contenu des variables. Comment expliquez vous la valeur de la variable r.


Remarque
Il n'est pas pertinent d'inclure dans des programmes des nombres comme 1500 sans préciser leurs significations et sans fournir un mécanisme pour les modifier au besoin.

En utilisant la commande du préprocesseur #define en début de fichier, on peut définir un nom symbolique (#define Somme 1500) et le réutiliser par la suite (A = Somme). Le préprocesseur remplacera le nom Somme par 1500 chaque fois qu'il le rencontrera dans le programme.




Exercice 2.4 --- Typage implicite.


Expliquer pourquoi le programme suivant :

int main(void){

 int a = 10;
 float b ;

 b = 1/(a/100) ;

 return 0 ;
}
 
compile mais provoque une erreur d'exécution.


2.2.3  Le type char

En C, le type char correspond aux entiers signés codables sur 1 octet. Un bit étant réservé pour le signe, il s'agit des entiers compris entre 27-1(=127) et -127. Le type unsigned char désigne les entiers non signés codables sur 1 octet (de 0 à 255).

Puisque les variables de types char codent des entiers, on peut les convertir en ce type par la commande :
char foo ='a' ;
int  bar = (int) foo ; /* (int) est un op\'erateur de convertion de type */
Par le biais d'une table, ces entiers sont associés à des caractères ; le standard American Standard Code for Information Interchange est consultable dans le manuel (man ascii).

La norme ISO 8859-1 complète cette table afin de coder les lettres accentuées utilisées en Europe de l'ouest (man iso_8859_1 pour plus de détails).




Exercice 2.5 --- Les fonctions putchar et getchar.


La fonction int putchar (int c); prend en entrée un entier représentant le code ascii d'en caractère et affiche ce caractère sur la sortie standard.

La fonction int getchar (void); récupère un caractère dans l'entrée standard et le retourne.

L'usage de ces fonctions nécessite l'ajout de la directive #include <stdio.h> à votre code.

Construisez un programme qui permette à l'utilisateur de saisir une lettre minuscule au clavier et affiche la majuscule correspondante à l'écran (ne vous occupez pas de la gestion d'erreur).

Même exercice mais la lettre est supposée être stockée dans un fichier et la majuscule doit être stockée dans un autre (utilisez les redirections du shell).







Exercice 2.6 --- Séquence d'échappement.


Les caractères ASCII reçèlent quelques suprises. Déternimez ce que provoque l'affichage des caractères suivants :
'
'\n' '\t' '\b' '\r' '\"' '\\' '\0' '\a' '\?' '\'' '\v'






Exercice 2.7 --- Étude du type char.


En utilisant les tables de codages des caractères et en gardant à l'esprit le codage d'un entier sur un octet, prévoyez le résultat du programme suivant :
#include <stdio.h>

int main(void){

  unsigned char bar = 'a' + 127 ;
  char foo = bar+256 ;

  printf("Le charact\\`ere %c correspond \\`a l'entier %d.\n",bar,(int) bar) ;
  printf("Le charact\\`ere %c correspond \\`a l'entier %d.\n",foo,(int) foo) ;

  return 0 ;
}
 






Exercice 2.8 --- Choix de typage.


Traduisez les déclarations suivantes en C, sachant que les variables sont destinées à continir les ensembles de nombres indiqués. Choisissez les types les plus économiques en terme d'espace mémnoir, sans perdre en précision.
entier COMPTEUR {0 ,..., 300}
entier X,Y {-120 ,..., 100}
entier MESURE {-10 ,..., 104}
r\'eel SURFACE1 {0.5 ,..., 150075}
r\'eel SURFACE2 {-12 ,..., 1500750.5}
entier N1 {0 ,..., 210}
entier N2 {-47 ,..., 47}
entier N3 {0 ,..., 326}
entier N4 {-1280 ,..., 1285}
bool\'een TROUVE {vrai, faux}






Exercice 2.9 --- Les constantes.


Quel(s) type(s) numérique(s) pouvez-vous utiliser pour les groupes de nombres suivants ?
  1  12   4  0   -125
  1  12  -4  0    250
  1  12   4  0    250
  1  12  -4  0.5  125
  -220    32000   0
  -3000005.000000001
  410    50000    2
  410    50000    -2
  3.14159265      1015
  2*107           10000001
  2*10-7          10000001
  -1.05*1050      0.0001
  305.122212  0   -12
  12332 23.4 345LU 34.5L -1.0
  0xeba  0123l '\n' 1.23ul -1.0e-1
  0xFE0  40000  40000u 70000u 1e1f
  '0'   ' \0'   0      'O'
  67e0  '\r'    01001   0.0l  0XEUL

2.2.4  Expressions

En C, les expressions peuvent être difficile à comprendre. Il est donc vivement conseillé de ne pas abuser de la flexibilité du langage au début de votre apprentissage.




Exercice 2.10 --- Affectation.


Quel est le résultat des instructions suivantes :
#include <stdio.h>

int main(void){

  int a,b =0 ;

  a+=b-=20 ;

  return 0 ;
}
 






Exercice 2.11 --- Suite d'expressions.


L'opérateur virgule permet de définir une suite d'expressions ; ces dernières sont évaluées de la gauche vers la droite et la valeur de retour de la suite d'expressions est la dernière expression évaluée.

Que retourne le programme suivant. Testez votre réponse.
int main(void){
 /* une premi\`ere suite 
    d'expressions  */
 int a = 2, b = a ; 
 /* une seconde */
 return a+=b, b+=3 ;
}







Pour tout commentaire : Alexandre Sedoglavic.
Précédent Remonter Suivant