Division des entiers en Java

La division des entiers en Java est l'une des opérations arithmétiques les plus simples — et l'une des plus piégeuses si on oublie que / ne fait pas la même chose sur int que sur double.

Division entière avec /

Entre deux entiers, / donne le quotient tronqué vers zéro, sans décimale :

int a = 10 / 3;     // 3
int b = -10 / 3;    // -3  (tronqué vers 0, pas arrondi vers -∞)
int c = 7 / 2;      // 3
int d = 1 / 2;      // 0  — piège classique

Le reste s'obtient avec l'opérateur % :

int reste = 10 % 3;   // 1
int reste2 = 7 % 2;   // 1

Division par zéro

Le comportement varie selon le type :

int x = 10 / 0;       // ❌ ArithmeticException: / by zero
double y = 10.0 / 0;  // ✅ Infinity
double z = 0.0 / 0;   // ✅ NaN (Not a Number)

Les double respectent la norme IEEE 754 et ne lèvent pas d'exception. Les entiers, eux, n'ont pas de valeur pour représenter l'infini — d'où l'ArithmeticException.

Obtenir un résultat à virgule

Pour éviter la troncature, au moins un des deux opérandes doit être un double ou float :

double x = 10 / 3;          // 3.0 — Java divise en int PUIS convertit
double y = 10.0 / 3;        // 3.333…
double z = (double) 10 / 3; // 3.333…
double w = 10 / (double) 3; // 3.333…

C'est l'ordre d'évaluation qui fait tout : dans 10 / 3, les deux sont des int, la division est donc entière, et la conversion en double vient après.

Long, BigInteger

Pour des nombres très grands, préférez long (64 bits) ou BigInteger :

long grand = 10_000_000_000L / 3L;   // 3333333333

import java.math.BigInteger;
BigInteger a = new BigInteger("123456789012345678901234567890");
BigInteger b = BigInteger.valueOf(7);
BigInteger q = a.divide(b);
BigInteger r = a.remainder(b);
BigInteger[] qr = a.divideAndRemainder(b); // les deux en un appel

Arrondi au lieu de troncature

Si vous voulez arrondir au plus proche au lieu de tronquer vers zéro :

int arrondi = Math.round((float) 10 / 3);  // 3
int arrondi2 = Math.round((float) 7 / 2);   // 4 (3.5 → 4)

Pour arrondir vers le haut (ceiling) sans passer par double :

int ceil = (10 + 3 - 1) / 3;  // 4 — équivalent de Math.ceil(10.0/3)

L'astuce (a + b - 1) / b donne le plafond de a / b pour des entiers positifs.

Division entière signée vs non signée

Jusqu'à Java 7, Java ne connaît que la division signée. Depuis Java 8, Integer.divideUnsigned traite les opérandes comme non signés :

int resultatUnsigned = Integer.divideUnsigned(-1, 3); // 1431655765 (positif énorme)
int resultatSigned = -1 / 3;                          // 0

Rarement utile sauf pour du code bas niveau qui manipule des bits signés.

Cas pratiques

Convertir des secondes en heures/minutes

int total = 3725;
int heures = total / 3600;            // 1
int minutes = (total % 3600) / 60;    // 2
int secondes = total % 60;            // 5

Pagination

int total = 157, parPage = 20;
int pages = (total + parPage - 1) / parPage; // 8 — arrondi vers le haut

Moyenne entière sans overflow

// ❌ Risque d'overflow si a+b dépasse Integer.MAX_VALUE
int moyenne = (a + b) / 2;

// ✅ Sans overflow
int moyenneSafe = a / 2 + b / 2 + ((a % 2 + b % 2) / 2);

Récapitulatif

  • / entre entiers → quotient tronqué vers 0, pas de décimale.
  • / avec un double → division flottante.
  • % donne le reste.
  • Division par 0 : exception sur entier, Infinity/NaN sur flottant.
  • Arrondi au plus proche : Math.round après conversion en double.

Le piège principal reste 1/2 = 0 — gardez en tête qu'au moins un opérande doit être flottant dès que vous attendez une décimale.