Your browser doesn't support the features required by impress.js, so you are presented with a simplified version of this presentation.

For the best experience please use the latest Chrome, Safari or Firefox browser.

Java, une plateforme de programmation

Issu du Livre blanc :
  • Simplicité, Orienté Objet, et Familié
  • Robustesse et Sécurité
  • Architecture neutre et Portabilité
  • Interprété, Multithread, et Dynamique
  • Performances élevées

Simplicité, Orienté Objet, et Familié

  • Syntaxe proche de C++
  • Petite taille
  • Fonctionnalités orientées objet avancées
  • Suppression des complexités de C++

Robustesse et Sécurité

  • Early checking
  • Run-time checking
  • Allocation mémoire gérée par la JVM
  • Conçu pour rendre impossible certaines attaques

Architecture neutre et Portabilité

  • Bytecode
  • S'exécute partout où une JVM est présente
  • Taille et types de données spécifiés

Interprété, Multithread, et Dynamique

  • Exécution de bytecode
  • Chargement de code depuis Internet
  • Reflection

Performances élevées

  • Interprétation de bytecode plus lente...
  • Compilateurs JIT

Exemple de programme java


public class HelloWorld
{
    public static void main(String[] args)
    {
        System.out.println("Hello World");
    }
}

Exécuter un programme

 
Source java
javac
Bytecode java
java
Affichage
HelloWorld.java
HelloWorld.class
"Hello World"

Règles d'écriture

  • Nom de fichier : Le nom de fichier doit s'appeler comme la classe qu'il contient suivi de l'extension .java
  • Identificateurs : Un identificateur est composé de lettres et de chiffres et est sensible à la casse
  • Séparateurs : Deux identificateurs doivent être séparés par au moins un espace ou une fin de ligne.
  • Format libre : La mise en page du programme est totalement libre.
  • Indentation : Il est recommandé d'indenter son programme pour le rendre lisible.
  • Caractères accentués et spéciaux : Il est recommandé de pas utiliser de caractères spéciaux ou accentués dans les identificateurs

Bases du langage

  • Commentaires
  • Types primitifs de données
  • Types énumérés
  • Variables
  • Constantes
  • Méthodes
  • Opérateurs
  • Conversions et transtypages
  • Tableaux

Commentaires

/*
 *  Première classe d'exemple
 *  pour le cours Java 210
 */
public class HelloWorld
{
    /**
     * Point d'entrée du programme
     * 
     * @param args Tableau des arguments passés au programme
    */
    public static void main(String[] args)
    {
        //Affiche Hello World dans la console
        System.out.println("Hello World");
    }
}

Types primitifs de données

 Java est un langage fortement typé. Toute variable doit donc avoir un type.

Types primitifs prédéfinis en java

  • Entiers : int short long bytes
  • Réels : float double
  • Caractère : char
  • Vrai/faux : boolean

Entiers

Type Occupation en mémoire Intervalle (limites incluses)
byte 1 octet -128 à 127
short 2 octets -37 768 à 32767
int 4 octets -2 147 489 648 à 2 147 483 647
long 8 octets -9 223 372 036 854 775 808 à 9 223 372 036 854 775 807

Réels

Type Occupation en mémoire Intervalle (limites incluses)
float 4 octets +- 3.40282347 x 1038 6 ou 7 décimales significatives
double 8 octets +- 1.79769313486231570 x 10308 15 décimales significatives

Caractère

Booléen

Types énumérés

//Définition du type énuméré Taille
enum Taille {SMALL, MEDIUM, LARGE, EXTRA_LARGE};
//L'ordre de définition des constantes SMALL, MEDIUM... est important !

Variables

boolean enConge;//Déclaration de la variable enConge
enConge = false;//Initialisation de la variable en affectant la valeur false
int joursVacances = 25;//Déclaration et initialisation de la variable joursVacances en une ligne.
double salaire, prime;//Déclaration de deux variables en une ligne. Non recommandé.
System.out.println(salaire);//Erreur de compilation
Taille s = Taille.SMALL;//Déclaration d'une variable du type énuméré Taille
int a, var1, monEntier;// Déconseillé car non pertinent
double Salaire, primeFinAnnée; //Déconseillé car majuscule et accents
short mon Age, m@x;//Erreur car espaces ou caractères non alpha-numériques
boolean estPresent;//OK
int age,Age,AGE;//Trois variables différentes car sensible à la casse.
boolean public;//Interdit car public est un mot réservé de java

Constantes

public class ExempleConstantes {
    //Visible dans toute la classe
    public static final short NOMBRE_MOIS_ANNEE = 12;
    public static final short NOMBRE_TRIMESTRE_ANNEE = NOMBRE_MOIS_ANNEE / 3;
    public static void main(String[] args){
        final short NOMBRE_JOURS_SEMAINE = 7;//Visible uniquement dans main
        System.out.println("Nombre de mois dans l'année : " + NOMBRE_MOIS_ANNEE);
        NOMBRE_JOURS_SEMAINE = 9;//Interdit ! Erreur de compilation
    }
}

Méthodes

int auCarre(int x) 
{

  //Multiplie l'argument x par
  //lui-même et retourne du résultat
  return x * x;
}

//Appel de la méthode
System.out.println(auCarre(4));
//Affiche 16

public void afficheBonjour() 
{
  //Cette méthode ne fait qu'afficher
  //Pas de return
  System.out.println("Bonjour !");
}

afficheBonjour(); //Affiche "Bonjour !"

Opérateurs arithmétiques

int quinze = 3 * 5; int deux = quinze - 13;
int sept = quinze / deux; //Division entière car les variables sont des entiers
int un = 15 % 2; //Reste de la division entière de 15 par 2 (modulo)
double quinzeDouble = 15.0; 
double septVirguleCinq = quinzeDouble / 2;//Division entre un double et un entier
int x = 5; x++;//équivalent à x = x + 1; x vaut 6
int y = 2 * --x;//y vaut 10, x vaut 5
int z = 2 * x++;//z vaut 10, x vaut 6
x -= 2;//équivalent à x = x - 2; x vaut 4

Opérateurs relationnels et booléens

Test Signe Exemple
Egalité ==
4 == 5 // false
Différence !=
4 != 5 // true
"ET" logique &&
true && false // false.
"OU" logique ||
true || false // true
"NON" logique !
!true // false.
Infériorité < et <=
5 < 5 // true
5 <= 5 // true
Supériorité > et >=
4 > 5 // false
5 >= 5 // true
Opérateur ternaire ? et :
x < y ? x : y // Renvoie x si x < y, sinon renvoie y

Opérateurs binaires

Opération Signe Exemple
"ET" logique &
10 & 3 // 1010 & 0011 => 0010 soit 2
"OU" logique |
10 | 3 // 1010 | 0011 => 1011 soit 11
"OU" exclusif ^
10 ^ 3 // 1010 ^ 0011 => 1001 soit 9
"NON" logique ~
~10 // ~1010 => 0101 soit 5
Décalage de bits << ou >>
10 >> 1 // 1010 >> 1 => 0101 soit 5 (bit de pois faible perdu)
10 << 1 // 1010 >> 1 => 0100 soit 4 (bit de poids fort perdu)

Priorités des opérateurs

Expression Equivalent
a + b * c ou a || b && c a + (b * c) ou a || (b && c)
a * b + c * d ou a && b || c && d (a * b) + (c * d) ou (a && b) || (c && d)
-c * d ou !c && d (-c) * d ou (!c) && d
-a * -b + c ou !a && !b || c ( (-a) * (-b) ) + c ou ( (!a) && (!b) ) || c

Conversions

Exemple de perte de précision :

int n = 987654321;
float f = n;// f vaut 9.8765434E8

Règles de conversions automatiques lors d'opérations arithmétiques :

  • Si un des opérandes est un double, l'autre sera converti en double
  • Sinon, si un des opérandes est un float, l'autre sera converti en float
  • Sinon, si un des opérandes est de type long, l'autre sera converti en long
  • Sinon les deux opérandes seront convertis en int
Converions

Transtypages (cast)

Exemples de transtypage :

//Transtypage double -> int
double d = 4.567;
int n = (int)d;// d vaut 4 (la partie décimale est perdue)

//Transtypage int -> short
int i = 55000;
short s = (short)i; //s vaut -10536...

Tableaux

//Déclaration d'un tableau d'entier
int[] tableauEntier, tableauEntier2; //Le tableau est déclaré mais non initialisé

//Initialisation du tableau
tableauEntier = new int[50]; //Le tableau est vide et peut contenir jusqu'à 50 valeurs
tableauEntier2 = new int[] {5, 4, 3, 8, 5}; //Déclare, initialise et remplit le tableau

//Insertion d'un élément dans le tableau
tableauEntier[0] = 5; //Met l'entier 5 dans le premier élément du tableau.
tableauEntier[50] = 10; //Exception, on essaye d'insérer au 51e élément du tableau.

//Accès à un élément dans un tableau
int premierElement = tableauEntier[0];

//Obtenir la taille du tableau
int tailleTableau = tableauEntier.length;

Manipulation de tableaux

//Copie de tableaux
//Attention, ceci n'est pas une copie ! 
tableauEntier = tableauEntier2;// tableauEntier2 et tableauEntier font maintenant référence au même tableau
//Pour copier on utilise Arrays.copyOf(tableauCible, nbElementsACopier) ou Arrays.copyOfRange(tableauCible, indexDepart, indexFin);
tableauEntier = Arrays.copyOf(tableauEntier2, tableauEntier2.length);
tableauEntier = Arrays.copyOfRange(tableauEntier2, 0, tableauEntier2.length);

//Tri d'un tableau
Arrays.sort(tableauEntier);

//Recherche dans un tableau trié
int i = Arrays.binarySearch(tableauEntier, 5); //Renvoie l'indice de la valeur 5 si elle est trouvée ou une valeur négative sinon

//Comparaison de tableau
boolean egal = Arrays.equals(tableanEntier, tableauEntier2); //Renvoie true si les tableaux ont la même longueur et le même contenu

//Remplissage d'un tableau
Arrays.fill(tableanEntier, 6); //Remplie tous les éléments du tableau avec la valeur 6

Tableaux multi-dimensionnels

//Déclaration d'un tableau bidimensionnel
char[][] tableau2D;// [][] pour deux dimensions, [][][] pour trois dimensions...

//Initialisation d'un tableau bidimensionnel
tableau2D = new char[3][4];//Equivalent à un tableau de 3 colonnes et 4 lignes
char [][] sudoku = {
    {'2', '1', '9'},
    {'8', '4', '3'},
    {'6', '7', '?'}
}; // Il n'est pas nécessaire de définir les limites du tableau lorsqu'on connait tous ses éléments

//Accès à un élément du tableau bidimensionnel
char i = sudoku[0][1];//i vaut '1'

//Affectation d'un élément du tableau bidimensionnel
sudoku[2][2] = '5';//La valeur '?' est remplacée par '5'

Flux d'exécution

  • Portée d'un bloc
  • Conditions
  • Boucles
  • Interruptions

Portée d'un bloc

public static void main(String[] args)
{
    int entierGlobalMethode = 5;
    {
        System.out.println(entierGlobalMethode); //entierGlobalMethode est accessible ici
        int entierLocalBloc = 4;
        {
            System.out.println(entierGlobalMethode); //entierGlobalMethode est accessible ici
        }
        int entierGlobalMethode = 5; //Exception : entierGlobalMethode est déjà défini
    }
    System.out.println(entierLocalBloc); //Exception : entierLocalBloc n'est plus accessible ici
    int entierLocalBloc = 4; //entierLocalBloc n'est plus accessible, il peut être de nouveau défini
}

Conditions

boolean estStrictementPositif = false; int monEntier = 5;
if(monEntier > 0)
    estStrictementPositif = true;
    System.out.println(monEntier + " est supérieur ou inférieur à 0"); //Attention, exécuté systématiquement !

if(estStrictementPositif) // équivalent à if(estStrictementPositif == true)
{
    System.out.println(monEntier + " est strictement supérieur à 0");
    appelMethode1(monEntier); //Deux instructions, donc nécessité d'utiliser un bloc { }
}
else if (monEntier < 0) //Plusieurs else if peuvent être enchaînés pour tester plusieurs cas
{
    System.out.println(monEntier + " est strictement inférieur à 0");
    appelMethode2(monEntier);
}
else { //Si aucune des conditions précédentes n'est remplie
    System.out.println(monEntier + " est égal à 0");
    appelMethode3(monEntier);
}

Conditions multiples

int position = 1;       
switch (position) {
    case 1:
    case 2:
    case 3:
        System.out.println("Sur le podium, bien joué !");
        break;
    case 4:
        System.out.println("Quatrième, aux portes du podium !");
        break;
    case 5:
        System.out.print("Pas si mal, cinquième ou ");
    case 6:
        System.out.println("sixième... Bel effort !");
        break;
    default:
        System.out.println("Loin derrière, merci d'avoir participé !");
        break;
}

Boucles while

int[] tableauFibonacci = {0, 0, 1, 2, 3, 5, 8, 13, 21, 34, 55};
int index = 0; int limite = 5; int taille = tableauFibonacci.length;
System.out.println("Affichage des " + limite + " premiers éléments de la suite de Fibonacci :");
while(index < limite && index < taille)
{
    System.out.println(tableauFibonacci[index++]); 
}
// Si la condition n'est pas vérifiée d'entrée
// rien n'est affiché

ou

do
{
    System.out.println(tableauFibonacci[index++]); 
}
while(index < limite && index < taille);
//Le premier élément de la suite sera affiché 
//même si la condition n'est pas vérifiée

Boucles for

int[] tableauFibonacci = {0, 0, 1, 2, 3, 5, 8, 13, 21, 34, 55};
System.out.println("Affichage de tous les éléments de la suite de Fibonacci :");
//for(inialisation ; condition ; incrémentation)
for(int i = 0; i < tableauFibonacci.length; i++)
{
    //A chaque itération, l'index i est
    //incrémenté tant qu'il ne dépasse
    //pas la taille du tableau
    System.out.println(tableauFibonacci[i]); 
}

ou

//for(element : collection)
for(int element : tableauFibonacci)
{
    //A chaque itération, element contient 
    //l'élément suivant du tableau jusqu'à
    //la fin
    System.out.println(element); 
}

Bonus Java 8

Arrays.stream(tableauFibonacci).forEach(System.out::println);

Interruptions

int[] tableauFibonacci = {0, 0, 1, 2, 3, 5, 8, 13, 21, 34, 55};

//On sort dès qu'une valeur est supérieur à 4
for(int element : tableauFibonacci)
{
    if(element > 4){
      break;
    }
    //La portion de code ci-dessous ne sera pas exécutée
    //lorsque la variable element vaudra 5
    System.out.print(element + ", "); 
    
}//Affichage 0, 0, 1, 2, 3, 
char [][] sudoku = {
    {'2', '9', '?'}, {'8', '4', '3'}, {'6', '7', '1'}
};

parcours_boucle: //Etiquette parcours_boucle
for(int i = 0; i < 3; i++){
    for(int j = 0; j < 3; j++){
      if(sudoku[i][j] == '?'){
        break parcours_boucle; //On sort des deux boucles
      }
      System.out.print(sudoku[i][j] + ", "); 
    } 
}//Affichage 2, 9, 

Interruptions

int[] tableauFibonacci = {0, 0, 1, 2, 3, 5, 8, 13, 21, 34, 55};

//On passe au tour de boucle suivant dès qu'une valeur paire
for(int element : tableauFibonacci)
{
  if(element % 2 == 0){
    continue;
  }
  //La portion de code ci-dessous ne sera pas exécutée
  //lorsque la variable element est paire
  System.out.print(element + ", "); 
  
}//Affichage 1, 3, 5, 13, 21, 55 

Exceptions

  • Fautes de saisie utilisateur
  • Ressources inexistantes
  • Problèmes réseaux
  • Problèmes matériels
  • Erreurs de programmation
  • ...

Les RuntimeExceptions

int[] tableauFibonacci = {0, 0, 1, 2, 3};
for(int i = 0; i < 6; i++){
  //Lorsque i va valoir 5, une exception va être levée
  //et va interrompre le traitement
  System.out.print(tableauFibonacci[i] + ", "); 
}//Affichage : 0, 0, 1, 2, 3 
=> Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: 5 at Fibonacci.main(Fibonacci.java:17)
int[] tableau = {5, 1, 0, 3};
for(int i = 0; i < tableau.length; i++){
  System.out.print(15 / tableau[i] + ", ");
}
=> Exception in thread "main" java.lang.ArithmeticException: / by zero at Fibonacci.main(Fibonacci.java:17)

Les exceptions sous contrôle

Faire gérer l'exception par le niveau supérieur

methodeRuntimeException() throws RuntimeException {
  ...
  throw new RuntimeException("Erreur...");
} 

//On ne gère pas les RuntimeException
methodeRuntimeException();

//On signale au programmeur que cette méthode peut lancer des
//exceptions de type IOException ou EOFException qu'il faudra gérer
methodeAutreException() throws IOException, EOFException{
  ...
  throw new IOException("Erreur...");
  ...
  throw new EOFException("Erreur...");
}

Gérer l'exception localement

try {
  methodeAutreException();
} catch(IOException exception) {
  //Gérer l'exception IOException
  ...
} catch(EOFException exception) {
  //Gérer l'exception EOFException
  ...
} finally() {
  //Dans tous les cas (exception ou pas), effectuer ce traitement
  ...
}

Conseils sur l'utilisation des exceptions

  • La gestion des exceptions ne doit pas remplacer un test simple
  • Ne pas gérer trop finement les exceptions
  • Respecter la distinction entre exceptions hors contrôle et exceptions sous-contrôle
  • Ne pas gérer silencieusement les exceptions
  • Ne pas renvoyer de valeur par défaut au lieu de lever une exception
  • Ne pas hésiter à renvoyer des exceptions aux niveaux supérieurs

Chaînes

La classe String

//Déclaration d'un objet de type String
String chaine; //chaine sera destinée à contenir une référence à un objet de type String

//Déclaration et initialisation d'un objet de type String
String chaine1 = ""; //référence à une chaîne vide
String chaine2 = new String(); //référence à une nouvelle chaîne vide 
String chaine3 = new String("Hello"); //référence à une chaîne contenant "Hello"
String chaine4 = "Hello";// Le compilateur crée automatiquement un objet de type String contenant "Hello"

Manipulation de chaînes

Opération Méthode retour Exemple
Longueur length() int
"Hello".length();//5
Concaténation concat(String chaineAConcatener) String
"Hello".concat(" World");//"Hello World"
"Hello" + " World";//Equivalent avec l'opérateur +
Egalité equals(String chaineAComparer) boolean
"Hello".equals("World");//false
"Hello" == "Hello";//true, même références
new String("Hello") == "Hello";//false, références différentes
"HELLO".equalsIgnoreCase("hello");//true
Sous-chaînes substring(int indexDebut, int indexFin) String
"Hello".substring(2, 4);//"ll"
"Hello".substring(2, 5);//"llo"
"Hello".substring(2);//"llo", par défaut jusqu'à la fin
Suppression des espaces de début et fin trim() String
"  Hello World ".trim();//"Hello World"
Remplacement replace(String recherche, String remplacement) String
"Hello World".replace("o", "0");//"Hell0 W0rld"
"Hello World".replace("World", "WORLD"); //"Hello WORLD"

Manipulation de chaînes

Opération Méthode retour Exemple
Début/Fin startsWith(String) et endsWith(String) boolean
"Hello".startsWith("He");//true
"Hello".startsWith("he");//false
"Hello".endsWith("o");//true
Rercherche contains(String chaineARechercher) boolean
"Hello".contains("el");//true
Casse toUpperCase() ou toLowerCase() String
"Hello".toUpperCase();//"HELLO"
"Hello".toLowerCase();//"hello"
Expression régulière matches(String regex) boolean
"hello".matches("[a-z]*");//alpha minuscule : true
"hello".matches("[0-9]*");//numérique entre 0 et 9 : false
Séparation split(String regex) String[]
"Hello World !".split(" ");//["Hello", "World", "!"]
"Hello World !".split(" ", 2);//["Hello", "World !"]
Recherche index indexOf(String recherche) ou lastIndexOf(String recherche) int
"Hello World".indexOf("X");//-1, non trouvé
"Hello World".indexOf("W");//6
"Hello World".indexOf("o");//4, première occurence
"Hello World".lastIndexOf("o");//7, dernière occurence

La console

Afficher dans la console

System.out.print("Hello ");
System.out.println("World !");
System.out.print("How are you ?");
//Hello World !
//How are you ?

Lire dans la console

System.out.println("Quel est votre nom ?");
Scanner scanner = new Scanner(System.in);

String ligneSaisie = scanner.nextLine();
//Je tape John suivi de entrée
System.out.println("Hello " + ligneSaisie);
//Hello John
scanner.close();//Appeler lorsque les saisies sont terminées

Bonus

  • La récursivité
  • Maitriser son IDE
  • Les méthodes à ellipse

Récursivité


static int factorielle(int nombre) {
    if (nombre == 1) {
        return 1;
    } else {
        return (nombre * factorielle(nombre - 1));
    }
}

Maitriser son IDE

  • Auto-complétion
  • Deboguer
  • Indenter automatiquement
  • Réorganiser les imports
  • Renommer une classe, une méthode, une variable
  • Refactorer
  • Générer du code
  • Connaître les principaux raccourcis

Méthodes à ellipses

void affiche(String... textes) {
  for(String texte : textes){
    System.out.println(texte);
  }
}

affiche("Hello");
affiche("Hello", "World");

void afficheObjectXFois(int nbFois, Object... objects) {
  for (int i = 0; i < nbFois, i++){
    separeMotEspaces(objects);
  }
}

afficheObjectXFois(5, "Hello");//Affiche 5 fois Hello
afficheObjectXFois(1, "Hello", 50, true);//Affiche Hello 50 true