... | @@ -67,132 +67,163 @@ Par exemple, `byte[]` représente un tableau d’octets. |
... | @@ -67,132 +67,163 @@ Par exemple, `byte[]` représente un tableau d’octets. |
|
|
|
|
|
# Déclaration de variables, affectation
|
|
# Déclaration de variables, affectation
|
|
|
|
|
|
|
|
## Variables de type primitif
|
|
|
|
|
|
La déclaration d’un entier, d’un flottant, d’un booléen ou d’un caractère s’effectue de la même manière qu’en C.
|
|
La déclaration d’un entier, d’un flottant, d’un booléen ou d’un caractère s’effectue de la même manière qu’en C.
|
|
|
|
|
|
Il est possible de déclarer une variable n’importe où à l’intérieur d’un **bloc d’instructions** (délimité par `{}`).
|
|
Il est possible de déclarer une variable n’importe où à l’intérieur d’un **bloc d’instructions** (délimité par `{}`).
|
|
|
|
|
|
```java
|
|
```java
|
|
public static void main(String[] args) {
|
|
public static void main(String[] args) {
|
|
int answer = 42;
|
|
int answer;
|
|
...
|
|
...
|
|
|
|
answer = 42;
|
|
}
|
|
}
|
|
|
|
```
|
|
|
|
|
|
> : warning: La portée d’une variable est le bloc d’instructions dans lequel elle est déclarée. Elle est invisible et inutilisable en dehors.
|
|
> : warning: La portée d’une variable est le bloc d’instructions dans lequel elle est déclarée. Elle est invisible et inutilisable en dehors. Ici la variable `answer` n'est accessible que depuis la méthode `main`.
|
|
|
|
|
|
> :memo: Il est possible d’initialiser une variable lors de sa déclaration :
|
|
> :memo: Il est possible d’initialiser une variable lors de sa déclaration :
|
|
|
|
|
|
```java
|
|
```java
|
|
public static void main(String[] args) {
|
|
public static void main(String[] args) {
|
|
int i = 0;
|
|
int answer = 42;
|
|
float c;
|
|
|
|
c = 3; // une instruction
|
|
|
|
// notez au passage la syntaxe d’un commentaire de fin de ligne ...
|
|
|
|
/* ceci est un autre commentaire qui n’invalide pas le reste de la ligne... */
|
|
|
|
boolean b = (c>i);
|
|
|
|
System.out.println(b); // affiche la valeur de b sur la console et passe a la ligne
|
|
|
|
}
|
|
}
|
|
La déclaration d’un tableau en Java est en revanche différente de celle en C, elle fait appel à la notion de constructeur (à travers le mot-clé new). Ci-dessous est présenté un exemple de déclaration, initialisation et manipulation de tableau.
|
|
```
|
|
public static void main(String[] args)
|
|
|
|
{
|
|
## Variables de type tableau
|
|
// args est un tableau de chaînes de caractères représentant les arguments
|
|
|
|
// passés à l’application sur la ligne de commande
|
|
Les tableaux Java ressemblent aux tableaux de C :
|
|
// Contrairement à C, args[0] représente le premier "vrai" argument.
|
|
- ils possèdent un nombre fixé et non extensible de cases
|
|
1. Unicode (http://www.unicode.org) est une norme qui définit un jeu de caractères universel (qui comprend tous les caractères disponibles dans toutes les langues écrites) et plusieurs types de codages de longueurs fixes (16 bits ou 32 bits par caractère, respectivement appelés UTF-16 et UTF-32) ou variables (de 8 à 24 bits par caractère, appelé UTF-8). Java est conçu de base pour manipuler les caractères et les chaînes de caractères UTF-16 (il est même possible d’utiliser des caractères Unicode dans les codes sources.
|
|
- chaque case peut être lu ou écrite en utilisant l'indice de la case entre crochets ( par exemple `[1]`)
|
|
2
|
|
- les indices commencent à `0`
|
|
|
|
|
|
// Déclaration d’un tableau statique de 5 valeurs de type short
|
|
Mais les tableaux Java diffèrent des tableaux C sur trois points :
|
|
// (l’espace mémoire réservé n’est pas extensible)
|
|
|
|
short[] s = new short[5];
|
|
- le nombre de cases d'un tableau n'est jamais spécifiée lors de la déclaration de la variable
|
|
// Les indices, comme en C, varient de 0 à taille-1
|
|
- pour que le tableau existe, il faut l'allouer (via le mot-clé `new`).
|
|
s[0] = 3;
|
|
- on peut connaitre à postériori le nombre de cases du tableaux à l'aide de `.length`
|
|
s[1] = 4;
|
|
|
|
// le nom du tableau postfixé de .length désigne la capacité du tableau
|
|
L'exemple ci-dessus illustre ces analogies et différences :
|
|
s[2] = s.length;
|
|
|
|
// la précédence des opérateurs est identique à celle de C
|
|
```java
|
|
s[3] = s[2]*s[0]-s[1];
|
|
public static void main(String[] args) {
|
|
// On ne peut pas demander de manière simple l’affichage d’un tableau,
|
|
short[] shortArray;
|
|
// on obtiendrait non pas la liste, mais une valeur unique n’ayant rien à voir.
|
|
shortArray = new short[3];
|
|
// L’argument de println est une chaîne de caractères.
|
|
shortArray[0] = 3;
|
|
// Java se charge de convertir n’importe quel type en chaîne de caractères.
|
|
shortArray[1] = shortArray[0] * 2;
|
|
// On doit cependant concaténer plutôt qu’écrire s[0]+s[1] ...
|
|
shortArray[2] = shortArray[1] - 1;
|
|
// car sinon on afficherait non pas la liste mais la somme.
|
|
|
|
// s[0]+s[1] est converti automatiquement en int,
|
|
System.out.println(shortArray[0]);
|
|
// s[0]+"" ("" est la chaîne vide) est converti en chaîne de caractères (String)
|
|
System.out.println(shortArray.length);
|
|
// Affiche (sur la console) les éléments du tableau sur une ligne et passe à la ligne
|
|
|
|
System.out.println(s[0]+""+s[1]+""+s[2]+""+s[3]+""+s[4]);
|
|
|
|
}
|
|
}
|
|
1.6 Opérateurs arithmétiques, relationnels et logiques
|
|
```
|
|
Cette sous-section décrit rapidement l’ensemble des opérateurs utilisables en Java.
|
|
|
|
1.6.1 Les opérateurs arithmétiques et leurs priorités
|
|
:warning: Dans l'exemple précédent, à la première ligne le tableau n'existe pas encore. Il n'existe qu'à l'appel de l'allocateur (`new`), l'affectation de la variable permet ensuite de désigner le tableau et d'accéder à ces éléments.
|
|
|
|
|
|
|
|
# Opérateurs arithmétiques, relationnels et logiques
|
|
|
|
|
|
|
|
La suite décrit rapidement l’ensemble des opérateurs utilisables en Java, assez similaires à ceux utilisés en C.
|
|
|
|
|
|
|
|
## Opérateurs arithmétiques et priorités
|
|
|
|
|
|
On trouve en Java les mêmes opérateurs qu’en C (à l’exception de l’opérateur puissance) :
|
|
On trouve en Java les mêmes opérateurs qu’en C (à l’exception de l’opérateur puissance) :
|
|
— l’addition, notée +
|
|
— l’addition, notée `+`
|
|
— la soustraction, notée -
|
|
— la soustraction, notée `-`
|
|
— l’opposé, (opérateur unaire) noté -
|
|
— l’opposé, (opérateur unaire) noté `-`
|
|
— l’identité (opérateur unaire), notée +
|
|
— l’identité (opérateur unaire), notée `+`
|
|
— la multiplication, notée *
|
|
— la multiplication, notée `*`
|
|
— la division (entière si les deux opérandes sont de type entier), notée / — le reste de la division entière, noté %
|
|
— la division (entière si les deux opérandes sont de type entier), notée `/`
|
|
La priorité s’opère comme suit :
|
|
— le reste de la division entière (modulo), noté `%`
|
|
1. les opérateurs unaires - et + sont les plus prioritaires,
|
|
|
|
2. les opérateurs * et / ont ensuite la priorité la plus élevée,
|
|
Les priorités sont les suivantes :
|
|
3. viennent ensuite les opérateurs binaires + et -.
|
|
|
|
4. l’associativité s’effectue de gauche à droite pour des opérateurs de même priorité.
|
|
1. opérateurs unaires `-` et `+`
|
|
1.6.2 Les opérateurs relationnels et logiques et leurs priorités
|
|
2. opérateurs `*` et `/`
|
|
|
|
3. opérateurs binaires `+` et `-`
|
|
|
|
|
|
|
|
:warning: L’associativité s’effectue de gauche à droite pour des opérateurs de même priorité.
|
|
|
|
|
|
|
|
## Opérateurs relationnels et logiques et priorités
|
|
|
|
|
|
Les opérateurs relationnels sont au nombre de six :
|
|
Les opérateurs relationnels sont au nombre de six :
|
|
— inférieur à, noté <
|
|
|
|
— supérieur à, noté >
|
|
— inférieur à, noté `<`
|
|
— égal à, noté ==
|
|
— supérieur à, noté `>`
|
|
— inférieur ou égal à, noté <= — supérieur ou égal à, noté >= — différent de, noté !=
|
|
— égal à, noté `==`
|
|
3
|
|
— inférieur ou égal à, noté `<=`
|
|
|
|
— supérieur ou égal à, noté `>=`
|
|
2
|
|
— différent de, noté `!=`
|
|
Le langage Java compte enfin sept opérateurs « bit-à-bit » (dans l’ordre de priorité) :
|
|
|
|
— la négation bit-à-bit, notée ̃
|
|
Le langage Java comporte également sept opérateurs _bit-à-bit_ (dans l’ordre de priorité) :
|
|
— le décalage de n bits à gauche, noté <<
|
|
|
|
— le décalage de n bits à droite avec recopie du signe, noté >> — le décalage de n bits à droite sans recopie du signe, noté >>> — le ET bit-à-bit, noté &
|
|
— la négation bit-à-bit, notée ` ̃`
|
|
— le OU exclusif bit-à-bit, noté ˆ
|
|
— le décalage de _n_ bits à gauche, noté `<<`
|
|
— le OU bit-à-bit, noté |
|
|
— le décalage de _n_ bits à droite avec recopie du signe, noté `>>`
|
|
Instructions de contrôle
|
|
— le décalage de _n_ bits à droite sans recopie du signe, noté `>>>`
|
|
Le langage Java compte également trois opérateurs logiques :
|
|
— le ET bit-à-bit, noté `&`
|
|
— la négation logique, notée !
|
|
— le OU exclusif bit-à-bit, noté `ˆ`
|
|
— la conjonction logique, notée && — la disjonction logique, notée ||
|
|
— le OU bit-à-bit, noté `|`
|
|
|
|
|
|
|
|
Le langage Java compte trois opérateurs logiques :
|
|
|
|
|
|
|
|
— la négation logique, notée `!`
|
|
|
|
— la conjonction (ET) logique, notée `&&`
|
|
|
|
— la disjonction (OU) logique, notée `||`
|
|
|
|
|
|
La négation logique est l’opérateur le plus prioritaire. Les priorités des autres opérateurs sont iden- tiques et l’associativité s’effectue de gauche à droite.
|
|
La négation logique est l’opérateur le plus prioritaire. Les priorités des autres opérateurs sont iden- tiques et l’associativité s’effectue de gauche à droite.
|
|
Avant de présenter la syntaxe des différentes instructions de contrôle, rappelons d’abord qu’une ins- truction élémentaire (affectation, déclaration, appel de méthode, . . .) en Java doit être terminée par un point-virgule. Dans la suite, lorsque nous utiliserons le mot instruction, nous désignerons :
|
|
|
|
— soit une instruction élémentaire,
|
|
# Instructions de contrôle
|
|
— soit une instruction de contrôle,
|
|
|
|
— soit un bloc d’instructions (des deux types précédents), délimité par {}.
|
|
> :warning: une instruction élémentaire (affectation, déclaration, appel de méthode, . . .) en Java doit être terminée par un **point-virgule**.
|
|
Dans ce qui suit, les crochets ([]) sont utilisés pour dénoter le caractère optionnel d’une construction.
|
|
|
|
2.1 if/else
|
|
## _if/else_
|
|
if condition
|
|
|
|
{
|
|
L'instruction conditionnelle `if` / `else` est définie par :
|
|
instructions
|
|
- une condition (expression ayant une valeur booléenne), exprimée entre `()`
|
|
}
|
|
- un bloc d'instructions à exécuter si la condition est vraie
|
|
ou :
|
|
- (optionnel) un bloc d'instructions à exécuter si la condition est fausse
|
|
if condition
|
|
|
|
{
|
|
Un exemple sans bloc `else` :
|
|
instructions
|
|
|
|
|
|
```java
|
|
|
|
if (a==b) {
|
|
|
|
c = 3;
|
|
|
|
System.out.println(c);
|
|
}
|
|
}
|
|
else {
|
|
|
|
instructions
|
|
Un autre exemple avec un bloc `else` :
|
|
|
|
|
|
|
|
|
|
|
|
```java
|
|
|
|
if (a==b) {
|
|
|
|
c = 3;
|
|
|
|
System.out.println(c);
|
|
}
|
|
}
|
|
La condition doit être exprimée entre parenthèses, exemple :
|
|
|
|
if (a==b)
|
|
|
|
System.out.println("stop");
|
|
|
|
else
|
|
else
|
|
System.out.print(".");
|
|
c = 5;
|
|
4
|
|
}
|
|
|
|
```
|
|
|
|
|
|
|
|
> :pencil: s'il n'y a qu'une seule instruction dans le bloc `if` ou dans le bloc `else`, l'utilisation des accolades n'est pas obligatoire.
|
|
|
|
|
|
|
|
## _switch_
|
|
|
|
|
|
2.2 switch
|
|
La construction `switch` permet d’exprimer une liste de décisions. Sa syntaxe est la suivante :
|
|
La construction switch permet d’exprimer une liste de décisions. Sa syntaxe est la suivante :
|
|
|
|
switch (expression)
|
|
switch (expression) {
|
|
{
|
|
|
|
case valeur1 :
|
|
case valeur1 :
|
|
instructions
|
|
instructions
|
|
case valeur2 :
|
|
case valeur2 :
|
|
instructions
|
|
instructions
|
|
... default :
|
|
...
|
|
|
|
default :
|
|
instructions
|
|
instructions
|
|
}
|
|
}
|
|
|
|
|
|
Exemple :
|
|
Exemple :
|
|
|
|
|
|
|
|
```java
|
|
switch (a) {
|
|
switch (a) {
|
|
case 1 :
|
|
case 1 :
|
|
System.out.println("1");
|
|
System.out.println("1");
|
... | @@ -202,42 +233,71 @@ switch (a) { |
... | @@ -202,42 +233,71 @@ switch (a) { |
|
default :
|
|
default :
|
|
System.out.println(a);
|
|
System.out.println(a);
|
|
}
|
|
}
|
|
Il faut remarquer que les case ne sont que des étiquettes de branchement, aucun test n’y est effectué. L’expression est testée au début du switch et, selon sa valeur, le programme branche à l’étiquette correspondante et le flot d’instruction suit son cours. Ceci veut dire que s’il n’existe pas de rupture de flot de contrôle (voir break plus loin dans cette sous-section) les instructions à l’étiquette case adéquate et toutes les instructions aux étiquettes suivantes sont exécutées.
|
|
```
|
|
L’étiquette default permet de spécifier un comportement par défaut (lorsqu’aucune étiquette ne correspond à la valeur de l’expression) ou un post-traitement.
|
|
|
|
2.3 for
|
|
Les `case` ne sont que des étiquettes de branchement, aucun test n’y est effectué. L’expression est testée au début du `switch` et, selon sa valeur, le programme branche à l’étiquette correspondante et le flot d’instruction suit son cours. Ceci veut dire que s’il n’existe pas de rupture de flot de contrôle (comme `break` ou `return`) les instructions à l’étiquette `case` adéquate et toutes les instructions aux étiquettes suivantes seront exécutées.
|
|
for (instruction1; expression; instruction2)
|
|
|
|
{
|
|
L’étiquette `default` permet de spécifier un comportement par défaut, lorsqu’aucune étiquette ne correspond à la valeur de l’expression.
|
|
|
|
|
|
|
|
## Boucle _for_
|
|
|
|
|
|
|
|
La syntaxe de la boucle `for` est identique à celle de C :
|
|
|
|
|
|
|
|
```java
|
|
|
|
for (instruction1; expression; instruction2) {
|
|
instructions
|
|
instructions
|
|
}
|
|
}
|
|
L’instruction instruction1 est une instruction élémentaire exécutée une et une seule fois avant le premier tour de boucle. C’est en général la déclaration et l’initialisation du compteur de boucle.
|
|
```
|
|
L’expression booléenne expression est évaluée avant chaque tour de boucle et dénote une condition. Si cette condition n’est pas vérifiée, on ne rentre plus dans le corps de la boucle.
|
|
- `instruction1` est une instruction élémentaire exécutée une et une seule fois avant le premier tour de boucle. C’est en général la déclaration et l’initialisation du compteur de boucle.
|
|
L’instruction instruction2 est une instruction élémentaire exécutée à chaque fin de tour de boucle. C’est en général l’opération d’incrémentation ou de décrémentation du compteur de boucle.
|
|
- `expression` est évaluée avant chaque tour de boucle et dénote une condition. Si cette condition n’est pas vérifiée, on ne rentre plus dans le corps de la boucle.
|
|
|
|
- `instruction2` est une instruction élémentaire exécutée à chaque fin de tour de boucle. C’est en général l’opération d’incrémentation ou de décrémentation du compteur de boucle.
|
|
|
|
|
|
|
|
|
|
Exemple :
|
|
Exemple :
|
|
for(int i=0;i<7;i++)
|
|
|
|
{
|
|
```java
|
|
System.out.println(i);
|
|
for(int answer=0;i<=42;index++) {
|
|
|
|
System.out.println(answer);
|
|
}
|
|
}
|
|
5
|
|
```
|
|
|
|
|
|
|
|
## Boucle `while` et `do while` :
|
|
|
|
|
|
|
|
La syntaxe des boucles `while` est identique à celle de C :
|
|
|
|
|
|
2.4 while
|
|
```java
|
|
while (expression)
|
|
while (expression) {
|
|
{
|
|
|
|
instructions
|
|
instructions
|
|
}
|
|
}
|
|
2.5 do while
|
|
```
|
|
|
|
|
|
|
|
et
|
|
|
|
|
|
|
|
```java
|
|
|
|
|
|
do {
|
|
do {
|
|
instructions
|
|
instructions
|
|
}
|
|
}
|
|
while (expression);
|
|
while (expression);
|
|
La différence entre cette instruction de contrôle et la précédente tient dans le fait que l’expression dénotant la condition d’arrêt est évaluée à la fin de chaque tour de boucle plutôt qu’au début (ce qui signifie que l’instruction constituant le corps de la boucle est exécutée au moins une fois).
|
|
```
|
|
2.6 break et continue
|
|
|
|
Ces deux instructions sont des instructions de rupture de flot de contrôle. Alors que break peut être utilisée dans n’importe quelle instruction de contrôle ou bloc d’instructions, continue ne peut être utilisée que dans les itérations (c’est à dire for et les variantes de while).
|
|
La différence entre les deux boucles tient dans le fait que l’expression dénotant la condition d’arrêt est évaluée à la fin de chaque tour de boucle dans le `do while` plutôt qu’au début pour le `while` (ce qui signifie que l’instruction constituant le corps de la boucle est exécutée au moins une fois dans un `do while`).
|
|
L’instruction break permet de sortir immédiatement d’un bloc d’instruction ou d’une boucle. Par exemple, si une telle instruction termine chaque case d’un switch, alors uniquement le bloc d’instructions associé au case correspondant à une valeur de l’expression sera exécuté (et le default sera dans ce cas vraiment un traitement par défaut).
|
|
|
|
L’instruction continue permet quant à elle de court-circuiter le reste du corps d’une boucle pour redémarrer de suite un nouveau tour (en effectuant tout de même les traitements intervenant à chaque fin de tour).
|
|
## Instructions `break` et `continue`
|
|
|
|
|
|
|
|
Ces deux instructions sont des instructions de rupture de flot de contrôle.
|
|
|
|
|
|
|
|
`continue` ne peut être utilisée que dans les itérations (c’est à dire `for` et les variantes de `while`), `break` peut être utilisée aussi dans un `switch`.
|
|
|
|
|
|
|
|
L’instruction `break` permet de sortir immédiatement d'une boucle ou d'un `case` d'un switch`, l’instruction `continue` permet quant à elle de court-circuiter le reste du corps d’une boucle pour redémarrer de suite un nouveau tour.
|
|
|
|
|
|
> : warning: Une valeur immédiate entière (résultat d'un calcul par exemple) est implicitement de type **`int`**, ce qui peut poser problème si on essaye de l’affecter à une variable de type `byte`.
|
|
> : warning: Une valeur immédiate entière (résultat d'un calcul par exemple) est implicitement de type **`int`**, ce qui peut poser problème si on essaye de l’affecter à une variable de type `byte`.
|
|
|
|
|
|
:warning: Une valeur immédiate flottante est implicitement de type **`double`**, ce qui peut poser problème si on essaye de l’affecter à une variable de type `float`.
|
|
:warning: Une valeur immédiate flottante est implicitement de type **`double`**, ce qui peut poser problème si on essaye de l’affecter à une variable de type `float`.
|
|
|
|
|
|
En langage C, ce genre de problème se règle par un forçage de type (aussi appelé transtypage ou cast). Il en est de même en Java, le cast ayant la même syntaxe, consistant à faire précéder la valeur du type compatible entre parenthèses. Dans le cas du cast en float, il existe une abbréviation qui consiste à rajouter uniquement la lettre f derrière la valeur flottante (-3,2E-4f).
|
|
En langage C, ce genre de problème se règle par un forçage de type (aussi appelé transtypage ou cast). Il en est de même en Java, le cast ayant la même syntaxe, consistant à faire précéder la valeur du type compatible entre parenthèses. Dans le cas du cast en float, il existe une abbréviation qui consiste à rajouter uniquement la lettre f derrière la valeur flottante (-3,2E-4f).
|
|
|
|
|
|
|
|
|
|
|
|
Commentaires.
|
|
|
|
|
|
|
|
1. Unicode (http://www.unicode.org) est une norme qui définit un jeu de caractères universel (qui comprend tous les caractères disponibles dans toutes les langues écrites) et plusieurs types de codages de longueurs fixes (16 bits ou 32 bits par caractère, respectivement appelés UTF-16 et UTF-32) ou variables (de 8 à 24 bits par caractère, appelé UTF-8). Java est conçu de base pour manipuler les caractères et les chaînes de caractères UTF-16 (il est même possible d’utiliser des caractères Unicode dans les codes sources. |