Caml en bref: Exemples

Contacter l'auteur Pierre.Weis@inria.fr

Fichier créé en mai 1997.

Exemples de calculs entiers:

Mêmes conventions sur les précédences des opérateurs qu'en mathématiques: la multiplication a priorité sur l'addition.

1 + 2 * 3 = 7
Le moins unaire est noté ``-'': ainsi - x désigne l'opposé de x.
- (2 + 3) = -5
- 2 + 3 = 1

Exemples de calculs flottants:

Mêmes conventions sur les précédences des opérateurs qu'en mathématiques. Les constantes flottantes doivent impérativement contenir un point .. Les opérateurs sont tous suffixés par un point .:

-. (2.0 +. 3.0) = -5.0
-. 2.0 +. 3.0 = 1.0
Le moins unaire est noté -.: -. x désigne l'opposé de x.

Exemples de calculs sur chaînes:

#"Par " ^ "exemple";;
- : string = "Par exemple"

Les caractères spéciaux doivent être préfixés par le caractère d'échappement \. Par exemple \n désigne un retour chariot et \" une apostrophe. Les chaînes très longues peuvent être écrites sur plusieurs lignes terminées par un caractère d'échappement: les blancs écrits au début de la ligne suivante seront ignorés

#"Par exemple: \
   Ceci est une très \
   longue chaîne";;
- : string = "Par exemple: Ceci est une très longue chaîne"
#"Bonjour".[0];;
- : char = `B`

#let s = "Bonjour" in
s.[0] <- `b`;
s;;
- : string = "bonjour"

Exemples de calculs sur les caractères:

L'entier désigné par un caractère représentant un chiffre:

#let digit_of_char c = (int_of_char c - int_of_char `0`);;
digit_of_char : char -> int = <fun>

#digit_of_char `7`;;
- : int = 7
La minuscule correspondant à une lettre:
#let lower_case c = char_of_int (int_of_char c + 32);;
lower_case : char -> char = <fun>

#lower_case `A`;;
- : char = `a`
Conversion inverse:
#let upper_case c = char_of_int (int_of_char c - 32);;
upper_case : char -> char = <fun>

#upper_case `a`;;
- : char = `A`
Les caractères non imprimables sont dénotés par leur code Ascii (sur 3 digits) en décimal.
#`\007`;;
- : char = `\007`
#`\048`;;
- : char = `0`

Exemples de calculs booléens:

Mêmes conventions sur les précédences des opérateurs qu'en mathématiques: le ``et'' && a priorité sur le ``ou'' || (pour les booléens && est similaire à la multiplication et || joue le rôle de l'addition). Ainsi x || y && z est similaire à x + y * z et donc implicitement parenthésé comme x || (y && z).

Exemples de calculs sur rien:

Passer une ligne:

#print_newline();;

- : unit = ()
Sans l'argument (), l'évaluation de print_newline réussit, mais n'appelle pas la procédure: aucune ligne n'est imprimée.
#print_newline;;
- : unit -> unit = <fun>
(On obtient en résultat la procédure elle-même.)

Exemples de définitions de valeurs:

Un nom définit par un ``let'' prend définitivement sa valeur au moment de la définition (on ne peut pas changer cette valeur).

let pi = 4.0 *. atan 1.0;;
Une définition locale ne sert que pendant le temps d'un calcul: celui qui suit le mot-clef in.
#let x = 1 in x + 1;;
- : int = 2
#x;;
Entrée interactive:
>x;;
>^
L'identificateur x n'est pas défini.
On définit plusieurs noms en faisant suivre plusieurs définitions, séparées par le mot clef and:
#let max = 100
and min = 10;;
max : int = 100
min : int = 10

Exemples de définitions de fonctions:

Définition de la fonction aire qui calcule l'aire d'un carré de coté c

#let aire (c) = c * c;;
aire : int -> int = <fun>
Les parenthèses autour de l'argument sont facultatives:
#let cube x = x * x * x;;
cube : int -> int = <fun>
De même à l'appel:
#aire (4);;
- : int = 16
#aire 16;;
- : int = 256

Exemples de définitions récursives de fonctions:

Définition récursive simple let rec f x = ...:

#let rec fact x =
 if x = 0 then 1 else x * fact (x - 1);;
fact : int -> int = <fun>

Exemples de définition de fonctions par filtrage:

Pour les fonction définies par filtrage: l'argument est implicite, c'est celui qui sera confronté au filtrage:

#let rec fact = function
 | 0 -> 1
 | x -> x * fact (x - 1);;
fact : int -> int = <fun>
#fact 10;;
- : int = 3628800

Exemples de définition de fonctions à plusieurs arguments:

let rec f x y = ...:

#let périmètre long larg = 2 * (long + larg);;
périmètre : int -> int -> int = <fun>
Fonctions sans arguments: on donne () comme argument. Par exemple une procédure pll qui imprime deux retour-chariots successifs s'écrit:
#let pll () =
 print_newline();
 print_newline();;
pll : unit -> unit = <fun>
et s'appelle, comme toutes les procédures, en lui appliquant ().
#pll ();;


- : unit = ()

Exemples d'appels de fonctions:

Les règles utilisées en Caml pour les opérateurs et fonctions sont analogues aux conventions des mathématiques pour les fonctions trigonométriques.

Argument simples (variables et nombres positifs): parenthèses facultatives.
Analogie trigonométrique: sin x, sin pi

Argument complexe: les parenthèses sont obligatoires.
Analogie trigonométrique: sin (x + y)

#let double x = x * 2;;
double : int -> int = <fun>

#double (1 + 2);;
- : int = 6

#double (-1);;
- : int = -2

Sans parenthèses, la signification change:

#double 1+2;;
- : int = 4

Sans parenthèses, l'argument est interprété différemment (ici comme la soustraction de double et 1):

#double -1;;
Entrée interactive:
>double -1;;
>^^^^^^
Cette expression est de type int -> int,
mais est utilisée avec le type int.

Priorité des opérateurs

En Caml, les priorités des opérateurs sont une généralisation des conventions des mathématiques pour les fonctions trigonométriques.

Exemples de filtrage:

Avec des filtres constants

 let rec fact = function
 | 0 -> 1
 | n -> n * fact (n - 1);;

Avec des filtres variables

 let rec fib = function
 | 0 -> 1
 | 1 -> 1
 | n -> fib (n - 1) + fib (n - 2);;

Avec des filtres intervalles

 let lettre = function
 | `a` .. `z` | `A` .. `Z` -> true
 | _ -> false;;

Avec des clauses gardées

 let lettre = function
 | c when c >= `a` && c <= `z`
       || c >= `A` && c <= `Z` -> true
 | _ -> false;;

Exemples d'utilisation des références:

On se sert de références pour définir des compteurs ou variables des langages impératifs traditionnels. On définit la fonction factorielle avec une boucle for et un accumulateur définit par une référence:

#let fact x =
 let res = ref 1 in
 for i = 1 to x do
  res := i * !res
 done;
 !res;;
fact : int -> int = <fun>
#fact 10;;
- : int = 3628800

Exemples d'utilisation des vecteurs:

Définition:

#let v = [| 0; 1; 2 |];;
v : int vect = [|0; 1; 2|]
#let v1 = make_vect 3 0;;
v1 : int vect = [|0; 0; 0|]
Accès et modification:
#v.(0);;
- : int = 0
#v.(0) <- 1;;
- : unit = ()
#v;;
- : int vect = [|1; 1; 2|]

Parcours:

#for i = 0 to vect_length v - 1 do
 print_int v.(i); print_string "; ";
done;;
1; 1; 2; - : unit = ()

Exemples d'utilisation des listes:

Définition:

#let l = [ 0; 1; 2 ];;
l : int list = [0; 1; 2]
#let l1 = 0 :: 1 :: 2 :: [];;
l1 : int list = [0; 1; 2]

Accès: par filtrage:

#match l1 with
 | x :: rest -> x
 | [] -> failwith "vide: impossible";;
- : int = 0

Pas de modification physique possible, mais on peut définir une fonction qui modifie un élément d'une liste:

let rec change n v = function
 | [] -> raise Not_found
 | x :: rest ->
   if n = 0 then v :: rest else x :: change (n - 1) v rest;;
change : int -> 'a -> 'a list -> 'a list = <fun>

Parcours: on utilise des itérateurs prédéfinis. map pour obtenir la liste des résultats de l'application d'une fonction. do_list pour appliquer une procédure à tous les éléments de la liste.

#let l1 = [4; 2];;
l1 : int list = [4; 2]
#do_list print_int l1;;
42- : unit = ()
#do_list (function i -> print_int i; print_string "; ") l1;;
4; 2; - : unit = ()


Page de présentation de Caml Dernière modification: vendredi 26 mars 2004
Copyright © 1995 - 2004, INRIA tous droits réservés.

Contacter l'auteur Pierre.Weis@inria.fr