Allgemeine Fragen zu Klassen

filament

Erfahrenes Mitglied
Hallo Leute,

Habe mich jetzt etwas intensiver mit Klassen und Funktionen beschäftigt, da ich mein neustes Projekt von Grund auf mit OOP und Klassen strukturieren will.

Aber mir schwirren ein paar allgemeine Sachen im Kopf die ich da noch nicht zu 100% verstehe. (Habe mir zwei längere Tutorials ausgedruckt, die viel beschreiben. Aber meine Fragen gehen nicht ganz klar heraus.)

Variablen definieren:

Wann muss ich denn die Variablen tatsächlich deklarieren mit public/private $name? Nur wenn ich diese in der Klasse neu generiere über $this->name?

Oder auch wenn ich aus der Index.php die Klasse bzw. Funktion aufrufe? (z.B. meine funktion("test"); ) Weil ich deklariere doch dann die Funktion selbst über public function ($variable) {}?

Konstruktor / Destruktor

Habe gelesen diese beiden Funktionen werden innerhalb einer Klasse automatisch ausgeführt?

Das heißt wenn ich eine Klasse DB erstelle und im Konstruktor die Verbindung über mysqli herstelle und dem Destruktor die Verbindung wieder schließe und muss es dann nirgends erneut machen?

Optionale Variablen

Habe gelesen man kann optionale Variablen per Funktionen übergeben. Soweit so klar.

Kann ich diese nach einer Prüfung der ersten Variable genauso an eine andere Funktion weitergeben? Oder macht das keinen Sinn?

Mein Plan wäre hier in meiner DB Klasse nach Select, Insert etc. zu unterscheiden und dann per switch die jeweilige nächste Funktion aufrufen. Geht das auch einfacher?

Struktur

Für die DB Klasse eher Funktionen nutzen für die einzelnen Querys oder lieber für Select eine Klasse, für Insert eine etc.?

Ausgabe

Die Ausgabe kann ja nur ein Element enthalten. Muss ich dann bei mehreren Ausgabe Parametern einen Array nutzen?

Ich habe zudem gelesen man soll Return nutzen. Weil dann wird noch nicht gleich ausgegeben und man kann später entscheiden ob ja oder nein?

Außerdem habe ich was von Set und Get Methoden gelesen. Sind diese empfehlenswert?

Danke schonmal für Antworten im Voraus. Es werden später sicher noch einige Fragen folgen. ;)
 
Hi,

ich finde es klasse dass du den Weg objektorientiert programmieren gehst und die prozedurale Programmierung etwas zu Seit legst. Für mich war es am Anfang nicht so leicht das alles als Objekte zu sehen.

In der objektorientierten Herangehensweise ist erst einmal alles ein Objekt! Wenn du eine Website Programmiert hast könnte zum Beispiel das Kontaktformular ein Objekt sein, zur der Seite könnten es ein Warenkorb geben, der wiederrum ein Objekt ist.

Diese Objekte haben verschiedene Eigenschaften ($Variablen), zu diesen Eigenschaften kann es Funktionen geben (Methoden). Diese beiden paare Eigenschaften und Methoden bilden das Objekt.

Das Objekt Kunde könnte demnach die Eigenschaften, Kundennummer, Vor- Nachname haben. Die Methoden wäre z.B. für die Darstellung des Warenkorbs zu ständig sein, hinzufügen oder löschen.

Wenn wir uns nun vorstellen, es gibt 100 Kunden; Jeder Warenkorb wird unterschiedlich sein. Jeder Kunde hat eine andere Kundennummer. Das heißt also wir müssen ein individuellen Warenkorb entwickeln. Eine Klasse dient wie eine Blaupause für etwas:

Nehmen wir an, wir haben die Klasse Kunde

PHP:
class Kunde
{


  public $name;


  public function halloSagen()
  {
    echo "Hallo";
  }


}


Die Klasse wird mit dem Schlüsselwort „class“, Name der Klasse gefolgt von {}.

Public $name; wäre eine Eigenschaft public function halloSagen() wäre demnach eine eine Methode.
Nun müssen wir dieses Objekt erstmalig erstellen.

Ein konkretes Objekt erstellen wir mit dem Schlüsselwort new und dem Namen der Klasse. Dies weisen wir einer Variablen zu, über die Sie das Objekt der Klasse dann ansprechen können:

PHP:
$neuerKunde = new Kunde();

Dann können wir einzelnen Eigenschaften setzen beispiel "$name":

PHP:
$neuerKunde->name = "Sven";

Wir greifen nun also auf die Variable in der Klasse zu und füllen sie mit Sven.
Genauso greifen wir auch auf die Methoden der Klasse zu, müssen hier aber hinter dem Methodennamen die runden Klammern schreiben:

Code:
$neuerKunde->halloSagen();

Wichtig! Alle Methoden und Funktionen die in der Klasse definiert wurden, könnten Parameter übergeben werden.

PHP:
class Kunde
   {
     public $name;
     public function halloSagen()
     {
       echo "Hallo";
     }
   }

   $neuerKunde = new Kunde();
   $neuerKunde->name = "Sven";
   $neuerKunde->halloSagen();
   
   echo " ";

   echo $neuerKunde->name;


Konstruktor und Destruktor

In meinem Beispiel beziehe ich mich nun auf Kunden. Eine Klasse bzw. ein Kunde ohne Namen wäre nicht so ganz sinnig. Möchte ich nun sicher gehen, dass bei jedem Aufruf der Klasse bzw. ein Neuen Kunden ein Name angegeben werden muss kann ich ein Konstruktor nutzen.

__construct() wird automatisch aufgerufen, wenn ein neues Objekt erstellt wird.

PHP:
class Kunde
   {
     public $name;

     public function __construct($name)
     {
       $this->name = $name;
    }

       public function halloSagen()
     {
      echo "Hallo {$this->name}";
     }

   }

Initialisieren wir nun eine neue Klasse

PHP:
$neuerKunde = new Kunde("Sven");

übergeben wir dem Konstruktor den Namen und weisen in der Variable $name zu.
Rufen wir nun
PHP:
$neuerKunde->halloSagen();

Sollte "Hallo Sven" ausgegeben werden. Der Destruktor Vernichtet einfach nur das Objekt. Dort könntest du, wie du auch gefragt hattest deine Datenbankverbindung schließen. Stelle dir nun selbst die frage, brauch jede Funktion deiner Klasse eine Aktive Datenbankverbindung?

Optionale Variablen

Natürlich, macht ja auch sinn. Wenn du etwas prüfen möchtest ob z.B. die KundenEmail Adresse schon vorhanden ist, könntest du die E-Mail an einer Methode übergeben der dir dann ein bool zurück gibt TRUE für vorhanden FALSE für nicht vorhanden.

Private and Public

leicht angedeutet: Eine Funktion die Privat ist kann nur innerhalb der Klasse genutzt werden. Sie ist nicht von außen aufrufbar. Alles was Privat ist bleibt innerhalb der Klasse selbst bei einer Vererbung kann nicht aus der Kindklasse drauf zugegriffen werden.

-- muss zwischenspeichern wichtiges Telefonat :D --
 
Danke für Deinen ausführlichen Beitrag und den hoffentlich genauso guten zweiten Teil, den ich noch vermute - wegen des letzten Absatzes. ;)

Wie gesagt habe ich mehrere Tutorials gelesen, studiert und auch bereits mit meiner Klasse angefangen. Im Grunde will ich lediglich den Datenbankzugriff in die Klasse DB packen. Ob ich später noch weitere Vorgehensweisen mit einer Klasse versehe kann ich noch nicht abschätzen.

Auf die Variablen zurück:

Du sagst ja alle Variablen auf die ich zurückgreife, müssen festgesetzt werden. In meiner DB Klasse möchte ich zunächst übergeben, ob es ein SELECT, INSERT, UPDATE oder DELETE wird.

Diesen Wert kann ich als Parameter übergeben. Aber ich muss es ja eigentlich nicht als Variable speichern. Von daher bin ich mir nicht sicher ob ich zum Beispiel eine Variable $query_typ festsetzen muss. Ich hoffe das ist nachvollziehbar wie ich es meine.

Zum Beispiel:

PHP:
new db("SELECT", "Parameter2", "Parameter3");

Dann würde ich in der Klasse folgende Funktion definieren:

PHP:
private function query_typ($query_typ, $parameter2, $parameter3) {

if ($query_typ == "SELECT"){

 // Funktion für Select aufrufen

}

}

Und mit dem Aufruf der neuen Funktion würde ich wieder die Parameter übergeben. In den Tutorials war nirgends erklärt bzw. aus Deinem Beitrag konnte ich jetzt auch nicht entnehmen, ob ich dann die Variable für die Klasse festlegen musste. Ich hätte es eher so vermutet, dass das nur der Fall ist, wenn ich diese innerhalb der Klasse oder Funktion festlege. Tue ich aber in meinem Beispiel ja eigentlich nicht?

Zum Konstruktor / Destruktor

Das heißt mit jeder Funktion innerhalb der Klasse würde dieser aufgerufen werden? Dann müsste ich wohl eher für meine DB Klasse eine extra Funktion connect und close machen und diese ausführen, klingt sinniger oder?

Macht es Sinn die Datenbank Zugänge statt in eine config.php in der Klasse zu schreiben? Und diesen dann einfach private zu geben? Denn außerhalb der Klasse wollte ich eigentlich nicht auf die DB zugreifen.
 
Hi,
sorry ist gestern etwas später geworden.

wenn wir davon ausgeben, dass du z.B.

PHP:
new db("SELECT", "Parameter2", "Parameter3");

nutzen würdest, benötigst du ein Konstruktor

PHP:
class demoClass
{
    public $parameter1;
    public $parameter2;
    public $parameter3;

    public function __construct($parameter1, $parameter2, $parameter3)
    {
        $this->parameter1 = $parameter1;
        $this->parameter2 = $parameter2;
        $this->parameter3 = $parameter3;
    }

    public function muster()
    {
        echo sprintf("Ich bin Parameter 1 %s. <br> Ich bin Parameter 2 %s <br> Ich bin Parameter 3 %s. <br>"
            , $this->parameter1, $this->parameter2, $this->parameter3);
    }
}


$demo = new demoClass("Max", "Hans", "Muster");
$demo->muster();

Ich befülle nun im Konstruktor die $parameter1/3 und kann so in jeder function() drauf zugreifen.

Ich würde das wie du es planst nicht umsetzten. In der Function zu prüfen was es genau ist und es an einer anderen function() übergeben. Macht für mich kein sinn.

Das Objekt beschreibt ein Adjektiv "Die Datenbank" der Verb wäre nun "SELECT", "INSERT" usw. für mich gehört die Beschreibung also das Verb in einer function()

PHP:
public function toSelect($table)
    {
        // TODO SELECT CODE
    }
 
    public function toInsert()
    {
        // TODO INSERT CODE
    }

Wenn ich schon vorher weiß, ich möchte ein Insert ausführen lass ich doch nicht ein Script prüfen was ich genau möchte. Ich kann von meinen script lieber ein

PHP:
$demo->toInsert($table)

ausführen. Ist für mich eine frage des Designs. Wie sauber lässt sich mein Code lesen.

[...]Beispiel eine Variable $query_typ festsetzen muss. Ich hoffe das ist nachvollziehbar wie ich es meine.

Nein dass musst du nicht! Das was die Function() entgegennimmt muss vorher nicht in der Klasse Deklariert sein.

Erfinde das Rad nicht neu. Die PDO Klasse von PHP ist verdammt gut & kann problemlos genutzt werden. Wenn du eine Klasse um die andere Klasse baust wäre es nur eine Ummantelung von etwas.

Ich würde mich da erstmal langsam rantasten. OOP ist mal eben nicht eine kleine sache :D ich selbst lerne es grade selbst & komme oft noch bei einfachen sachen in stottern. Daher könnte es möglich sein, dass ich vllt. auch falsch liege :D

Zum Anfang würde ich es so lösen:
PHP:
class db
{

    private $pdo;

    public function __construct()
    {
        $this->pdo = new PDO(
            'mysql:host=localhost;dbname=DBNAME;charset=utf8',
            'USERNAME',
            'PASSWORT'
        );
        return $this->pdo;
    }

    public function all($table)
    {
        $stmt = $this->pdo->query("SELECT * FROM `$table`");
        $stmt->execute();
        $posts = $stmt->fetchAll();
        return $posts;
    }

}
 
Zuletzt bearbeitet:
Zurück