Skip to content

6. Anwendungsübung – IMPOTS mit Objekten (impots_03)

Wir greifen die bereits zuvor behandelte Übung (Abschnitte 4.2 und 4.3) wieder auf, um sie mit einem Code PHP unter Verwendung einer Klasse zu lösen.


<?php

// Definition einer Klasse „Steuern“
class Impôts {

  // Attribute: die 3 Daten-Arrays
  private $limites;
  private $coeffR;
  private $coeffN;
  
  // Konstruktor

  public function __construct($IMPOTS) {
    // $IMPOTS: Name der Datei, die die Daten der Tabellen $limites, $coeffR und $coeffN enthält
    // Existiert die Datei $IMPOTS?
    if (!file_exists($IMPOTS)) {
      throw new Exception("Le fichier $IMPOTS n'existe pas");
    }//if
    // Blockweises Lesen der Datei
    $tables = file($IMPOTS);
    if (!$tables) {
      throw new Exception("Erreur lors de l'exploitation du fichier $IMPOTS");
    }//if
    // Erstellung der 3 Tabellen – es wird davon ausgegangen, dass die Zeilen syntaktisch korrekt sind
    $u = new Utilitaires(); // um über Hilfsfunktionen zu verfügen
    $this->limites = explode(":", $u->cutNewLineChar($tables[0]));
    $this->coeffR = explode(":", $u->cutNewLineChar($tables[1]));
    $this->coeffN = explode(":", $u->cutNewLineChar($tables[2]));
    }

  // --------------------------------------------------------------------------
  public function calculer($marié, $enfants, $salaire) {
    // $marié: ja, nein
    // $enfants: Anzahl der Kinder
    // $salaire: Jahresgehalt
    
    // Anzahl der Anteile
    $marié = strtolower($marié);
    if ($marié == "oui")
      $nbParts = $enfants / 2 + 2;
    else
      $nbParts=$enfants / 2 + 1;
    // ein halber Anteil zusätzlich, wenn mindestens 3 Kinder vorhanden sind
    if ($enfants >= 3)
      $nbParts+=0.5;
    // steuerpflichtiges Einkommen
    $revenuImposable = 0.72 * $salaire;
    // Familienquotient
    $quotient = $revenuImposable / $nbParts;
    // wird am Ende der Tabelle „Grenzwerte“ eingefügt, um die folgende Schleife zu beenden
    $this->limites[count($this->limites) - 1] = $quotient;
    // Steuerberechnung
    $i = 0;
    while ($quotient > $this->limites[$i])
      $i++;
    // da $quotient am Ende des Arrays $limites platziert wurde, wird die vorherige Schleife
    // darf nicht über das Array $limites hinausgehen
    // Nun kann die Steuer berechnet werden
    return floor($revenuImposable * $this->coeffR[$i] - $nbParts * $this->coeffN[$i]);
  }

}

// eine Klasse mit Hilfsfunktionen
class Utilitaires {

  public function cutNewLinechar($ligne) {
    // Die Zeilenende-Markierung von $ligne wird entfernt, falls vorhanden
    $L = strlen($ligne);  // Zeilenzahl
    while (substr($ligne, $L - 1, 1) == "\n" or substr($ligne, $L - 1, 1) == "\r") {
      $ligne = substr($ligne, 0, $L - 1);
      $L--;
    }//while
    // Ende
    return($ligne);
  }

}

// Test -----------------------------------------------------
// Definition der Konstanten
$DATA = "data.txt";
$RESULTATS = "resultats.txt";
$IMPOTS = "impots.txt";
// Die für die Steuerberechnung erforderlichen Daten wurden in die Datei IMPOTS geschrieben
// mit jeweils einer Zeile pro Tabelle in der Form
// „val1“:„val2“:„val3“,...
// wird ein Steuerobjekt angelegt
try {
  $I = new Impôts($IMPOTS);
} catch (Exception $e) {
  print $e->getMessage();
  exit;
}
// wird ein Hilfsobjekt erstellt
$u = new Utilitaires();

// Lesen der Benutzerdaten
$data = fopen($DATA, "r");
if (!$data) {
  print "Impossible d'ouvrir en lecture le fichier des données [$DATA]\n";
  exit;
}

// Ergebnisdatei wird geöffnet
$résultats = fopen($RESULTATS, "w");
if (!$résultats) {
  print "Impossible de créer le fichier des résultats [$RESULTATS]\n";
  exit;
}

// Die aktuelle Zeile der Datendatei wird ausgewertet
while ($ligne = fgets($data, 100)) {
  // Eventuelles Zeilenendezeichen wird entfernt
  $ligne = $u->cutNewLineChar($ligne);
  // Die drei Felder „verheiratet“, „Kinder“ und „Gehalt“ werden abgerufen, die $ligne bilden
  list($marié, $enfants, $salaire) = explode(",", $ligne);
  // Die Steuer wird berechnet
  $impôt = $I->calculer($marié, $enfants, $salaire);
  // Das Ergebnis wird eingetragen
  fputs($résultats, "$marié:$enfants:$salaire:$impôt\n");
  // Nächster Datensatz
}// while
// Dateien schließen
fclose($data);
fclose($résultats);

// Ende
print "Terminé\n";
exit;
?>

Die Datei [impots.txt]:

12620:13190:15640:24740:31810:39970:48360:55790:92970:127860:151250:172040:195000:0
0:0.05:0.1:0.15:0.2:0.25:0.3:0.35:0.4:0.45:0.5:0.55:0.6:0.65
0:631:1290.5:2072.5:3309.5:4900:6898.5:9316.5:12106:16754.5:23147.5:30710:39312:49062

Die Datei [data.txt]

oui,2,200000
non,2,200000
oui,3,200000
non,3,200000
oui,5,50000
non,0,3000000

Ergebnisse: dieselben wie in den Versionen mit Tabellen und Dateien.

Die Datei [resultats.txt]

oui:2:200000:22504
non:2:200000:33388
oui:3:200000:16400
non:3:200000:22504
oui:5:50000:0
non:0:3000000:1354938

Kommentare

  • Zeile 4: Die Klasse „Impôts“. Sie kapselt Daten und Methoden zur Berechnung der Steuer:
  • Daten: Zeilen 7–9 – dies sind die drei Datenarrays, die die Berechnung der Steuer ermöglichen. Diese drei Arrays werden vom Konstruktor in Zeile 13 anhand einer Textdatei initialisiert.
  • Methoden: Zeile 32 – Die Methode „calculer“ dient zur Berechnung der Steuer.
  • Zeilen 17, 22: Wenn der Konstruktor das Objekt Impôts nicht instanziieren kann, löst er eine Ausnahme aus.
  • Zeile 25: Die Klasse Utilitaires wurde definiert, um die Funktion cutNewLineChar zu kapseln.
  • Zeilen 26–28: Initialisierung der drei privaten Felder der Klasse Impôts
  • Zeile 32: Mit der Methode calculer der Klasse Impôts lässt sich die Steuer eines Steuerpflichtigen berechnen.
  • Zeilen 65–78: Die Klasse Utilitaires
  • Zeilen 89–94: Erstellung eines Objekts Impôts mit Behandlung einer möglichen Ausnahme. Bei dieser Erstellung wird die Textdatei $IMPOTS ausgewertet, um deren Inhalt in die drei privaten Felder des Objekts Impôts zu übertragen.
  • Zeile 96: Erstellung eines Objekts Utilitaires, um die Funktion cutNewLineChar nutzen zu können.