Exercice 1

Quel est l'affichage produit par le programme suivant :

import java.util.Arrays;

public class Exo11 {

    public static void main(String[] args) {
	int[][] x = { { 1, 2, 3 }, { 6 }, { 4, 5 } };
	System.out.println(x.length);
	for (int i = 0; i < x.length; i++) {
	    System.out.printf("x[%d] = ", i);
	    System.out.printf("%s%n", Arrays.toString(x[i]));
	}
	System.out.println(Arrays.deepToString(x));
	int k = 0;
	for (int[] u : x) {
	    System.out.printf("{ ");
	    for (int j : u) {
		System.out.printf("%d ", k + j);
		k++;
	    }
	    k = k - u.length + 1;
	    System.out.println("}");
	}
	System.out.println(k);
    }

}

On obtient l'affichage suivant :

3
x[0] = [1, 2, 3]
x[1] = [6]
x[2] = [4, 5]
[[1, 2, 3], [6], [4, 5]]
{ 1 3 5 }
{ 7 }
{ 6 8 }
3

Exercice 2

Écrire un programme qui réalise les opérations suivantes :

  1. demande à l'utilisateur une taille de matrice (c'est-à-dire un nombre de lignes et un nombre de colonnes) ;
  2. crée une matrice de la taille indiquée (sous forme d'un tableau de type int[][]) et la remplit de chiffres aléatoires (entiers entre 0 et 9 inclus) ;
  3. affichage la matrice sans utiliser les méthodes Arrays.toString et Arrays.deepToString ;
  4. à détermine et affiche la position du plus grand élément de la matrice : si la valeur en question apparaît plusieurs fois, on retiendra comme position la première ligne et la dernière colonne qui prend cette valeur.

Une solution possible est la suivante :

import java.util.Random;
import java.util.Scanner;

public class Matrice {

    public static void main(String[] args) {
	Scanner scan = new Scanner(System.in);
	System.out.print("Nombre de lignes = ");
	int nbLignes = scan.nextInt();
	System.out.print("Nombre de colonnes = ");
	int nbColonnes = scan.nextInt();
	int[][] matrice = new int[nbLignes][nbColonnes];
	Random rng = new Random();
	for (int i = 0; i < matrice.length; i++) {
	    for (int j = 0; j < matrice[i].length; j++) {
		matrice[i][j] = rng.nextInt(10);
	    }
	}
	for (int i = 0; i < matrice.length; i++) {
	    System.out.print("{ ");
	    for (int j = 0; j < matrice[i].length - 1; j++) {
		System.out.print(matrice[i][j] + ", ");
	    }
	    System.out.println(matrice[i][matrice[i].length - 1] + "}");
	}
	int maxL = 0;
	int maxC = matrice[0].length - 1;
	int vMax = matrice[0][maxC];
	for (int i = 0; i < matrice.length; i++) {
	    for (int j = matrice[i].length - 1; j >= 0; j--) {
		if (matrice[i][j] > vMax) {
		    vMax = matrice[i][j];
		    maxL = i;
		    maxC = j;
		}
	    }
	}
	System.out.printf("Le maximum vaut %d et est situé dans la ligne %d et la colonne %d.%n", vMax, maxL + 1,
			  maxC + 1);
	scan.close();
    }

}

On remarque dans cette solution l'utilisation d'une boucle qui parcourt chaque ligne à rebours (depuis la fin de la ligne vers le début). Cela permet de bien choisir parmi les colonnes contenant le maximum celle de plus grand numéro (la plus à droite). De la même façon, la boucle classique sur les lignes permet de choisir la ligne de numéro le plus petit (la première ligne) parmi celles contenant le maximum.

Exercice 3

Quel est l'affichage produit par le programme suivant :

public class Exo21 {

    public static void main(String[] args) {
	StringBuilder bla = new StringBuilder();
	bla.append("D");
	System.out.println(bla);
	String s = bla.toString();
	StringBuilder pouic = bla;
	char[] c = { 'A', 'B', 'C' };
	String t = "abcd";
	for (int i = t.length()-1; i >= 0; i--) {
	    if (i % 2 == 0) {
		bla.append(t.charAt(i));
	    } else {
		s = s + t.charAt(i);
	    }
	    if (i < c.length) {
		pouic.append(c[i]);
	    }
	    System.out.printf("%d %s %s %s%n", i, bla, s, pouic);
	}
    }

}

On obtient l'affichage suivant :

D
3 D Dd D
2 DcC Dd DcC
1 DcCB Ddb DcCB
0 DcCBaA Ddb DcCBaA

Exercice 4

Écrire un programme qui affiche un « sapin de noël » de la forme suivante :

    +
   *++
  ++*++
 +*+++++
++*+++++*
    H

On procédera de la façon suivante :

  1. le programme doit demander à l'utilisateur la taille du sapin (un entier n positif, 5 dans l'exemple ci-dessus) et une valeur réelle comprise entre 0 et 1, p (0,2 dans l'exemple ci-dessus) ;
  2. chaque ligne du sapin doit être construite complètement grâce à un StringBuilder puis affichée en entier avec une méthode println ou printf ;
  3. le sapin comprend n+1 lignes qu'on peut numéroter de 1 à n+1 :
    • les lignes 1 à n contiennent uniquement des espaces et les symboles + et * ;
    • la ligne numéro i contient 2i-1 symboles + et * et débute par n-i espaces ;
    • le choix entre les symboles + et * se fait aléatoirement avec la probabilité p de choisir * : on utilisera donc un objet Random et sa méthode nextDouble qui renvoie un nombre réel de [0,1] choisi uniformément. Il suffit de comparer la valeur obtenue avec p pour choisir le bon symbole ;
  4. la dernière ligne du sapin contient la lettre H centrée.

ATTENTION : vous ne devez pas afficher les lignes caractère par caractère.

Une solution possible est la suivante :

import java.util.Random;
import java.util.Scanner;

public class Sapin {

    public static void main(String[] args) {
	Scanner scan = new Scanner(System.in);
	System.out.print("Taille du sapin = ");
	int n = scan.nextInt();
	System.out.print("Probabilité de * = ");                
	double p = scan.nextDouble();
	Random rng = new Random();
	for (int i = 1; i <= n; i++) {
	    StringBuilder sb = new StringBuilder(n + 1);
	    for (int j = 0; j < n - i; j++) {
		sb.append(' ');
	    }
	    for (int j = 0; j < 2 * i - 1; j++) {
		if (rng.nextDouble() < p) {
		    sb.append('*');
		} else {
		    sb.append('+');
		}
	    }
	    System.out.println(sb);
	}
	StringBuilder sb = new StringBuilder(2 * n + 1);
	for (int j = 0; j < n - 1; j++) {
	    sb.append(' ');
	}
	sb.append("H");
	System.out.println(sb);
	scan.close();
    }

}

Exercice 5

On souhaite choisir au hasard un nombre premier arbitrairement grand, en utilisant les BigInteger. Pour ce faire on écrit un programme qui réalise les opérations suivantes :

  1. demande à l'utilisateur un nombre de chiffres, p, strictement supérieur à 21 et un entier k indiquant le niveau de certitude souhaité (cf plus bas) ;
  2. trouve un nombre premier à p chiffres grâce à la méthode ci-dessous :
    1. construit une chaîne de caractères de longueur p contenant des chiffres choisis aléatoirement (entre 0 et 9), et se terminant par un chiffre impair (on utilisera un StringBuilder) ;
    2. construit un BigInteger à partir de la chaîne en utilisant le constructeur adapté ;
    3. teste si le nombre obtenu est premier en utilisant sa méthode isProbablePrime avec le paramètre k ;
    4. recommence ces opérations si le nombre n'est pas premier ;
  3. affiche le nombre obtenu ainsi que le nombre de tentatives nécessaires à sa construction.

Une solution possible est la suivante :

import java.math.BigInteger;
import java.util.Random;
import java.util.Scanner;

public class Premier {

    public static void main(String[] args) {
	Scanner scan = new Scanner(System.in);
	int n = 0;
	while (n <= 21) {
	    System.out.print("Nombre de chiffres (au moins 21) = ");
	    n = scan.nextInt();
	}
	System.out.print("Niveau de certitude = ");
	int k = scan.nextInt();
	BigInteger prime;
	Random rng = new Random();
	int nb = 0;
	do {
	    StringBuilder s = new StringBuilder(n);
	    for (int i = 1; i < n; i++) {
		s.append(rng.nextInt(10));
	    }
	    s.append(1 + 2 * rng.nextInt(5));
	    prime = new BigInteger(s.toString());
	    nb++;
	} while (!prime.isProbablePrime(k));
	System.out.printf("Après %d tentatives, on a choisi : %s%n", nb, prime);
	scan.close();
    }

}