Hallo Zusammen,
lasst euch bitte nicht von vorne rein von dem Titel des Themas abschrecken.
Das Thema __autoload() ist hier schon ziemlich oft besprochen worden, wobei es meist um das Verständnis der Funktion an sich ging.
Bei meinem aktuellen Problem geht es aber nicht um das Verständnis der Funktion, sondern viel mehr, einen Weg zu finden, diese optimal zu verwenden.
Mir ist bewusst, dass es in dieser Richtung schon einige Lösungsansätze gibt. Aber vorerst möchte ich euch mal schildern wie es zu meiner gleich gestellen Fragen kommt.
Also wie viele von euch wissen, ist die __autoload() - Funktion, eine Interzeptor - Funktion, die automatisch aufgerufen wird, sobald ein Objekt einer Klasse mit dem "new"-Operator instanziiert werden soll, diese allerdings noch nicht deklariert ist. __autoload() bekommt also den Namen der aufgerufenen ( noch nicht deklarierten ) Klasse als Parameter und kann nun die entsprechende Klasse nachladen.
Dieses Muster findet man bereits in einigen Frameworks wieder. Viele dieser Lösungen sind sehr ähnlich. So löst das Zend - Framework das Problem so, das die Klassennamen Unterstriche enthalten, diese später durch slashes ersetzt werden und somit einen gültigen Pfad zur entsprechenden Klasse darstellen.
So, oder so ähnlich würde es aussehen:
Aus dieser Klassenbezeichnung wird also:
Dieser Lösungsansatz, ist mein persönlicher Favorit. Nur gibt es hier eine Sache die mich gewaltig stört. Und zwar ist das die Bezeichnung der Klassen im Code.
Habe ich beispielsweise eine Ordnerstruktur die so aussieht:
und:
Könnte ich diese beiden Dateien, oder eher die Klassen, die diese Dateien enthalten, nach Zend - Konventionen in dieser Form nachladen:
Diese Schreibweise macht den Code sicherlich nicht unleserlich, aber dennoch nicht sehr schön.
Nach weiteren Überlegungen dachte ich man könnte es folgendermaßen schöner machen:
Eine Instanziierung der Klasse Admin (für dieses Beispiel) würde so aussehen:
Die Unterstriche werden also einfach rausgelassen und der Klassenbezeichner im Code, entspricht dem Pfad der nach zuladenen Klasse im Camel Case format. Hier könnte man die __autoload() Funktion also mit regulären Ausdrücken ausstatten, die die Positionen der einzelnen Großbuchstaben ermittelt und zwischen diesen Vorkommnissen ( also User und Admin in diesem Beispiel) ein Slash setzen. Daraus würde dann wieder ein entsprechender Pfad erzeugt werden, der zum Nachladen der Klasse
genutzt werden kann.
Aber auch hier finde ich einige Punkte die mich Stören. Zum einen,
werden bei diesem Lösungsansatz die Klassenbezeichner im Code schwer leserlich, sobald die Ordnerstruktur zur entsprechenden Klasse mehr als 2 oder 3 Ordner betrifft.
So wird aus der Ordnerstruktur:
Ein Klassenbezeichner der so aussehen würde:
Also in diesem Beispiel sind es nicht einmal 2-3 Ordner und trotzdem sieht die Klassenbezeichnung im Code sehr unschön aus. Hier würde ich zum Beispiel
die Zend - Konvention vorziehen, da aus dem oben genannten Pfad folgende Klassenbezeichnung entstehen würde:
Ist meiner Meinung nach, die definitiv schönere Variante. Aber nun zurück zum eigentlichen Problem.
Ein weiterer Punkt der viele Probleme mit sich bringt, bei der Verwendung der Camel Case - Konvention ( ich nenne sie jetzt mal so ),
ist, dass die eigentlichen Dateinamen der Klassen auf nur einen ersten Großbuchstaben beschränkt sind.
Gut sichtbar ist dies in dem Beispiel von oben:
Das "Sql" beginnt ebenfalls mit einem Großbuchstaben, was bedeutet das also im Ordner "My" nach der Datei "Sql" gesucht werden würde.
So nun hab ich viel erzählt.
Meine Fragestellung ist folgende:
Ich würde mir wünschen Klassen ganz normal nach ihrem wirklichen Bezeichner zu instanziieren.
Das bedeutet also sowas wie:
Die __autoload() - Funktion soll mir nun also diese Klasse im System suchen.
Problem ist hier natürlich, das __autoload() nicht weiß, wo sie suchen muss. Dieses Problem gibt es in dem obigen Beispielen nicht.
Ich suche also nach einer Lösung, eine __autoload() Funktion zu implementieren, die mir allein anhand des Klassenbezeichners, den ich auch aufrufe, die Entsprechende Klasse nachäd.
Dies ist ja so ohne weiteres nicht möglich, wenn __autoload() nicht weiß, wo sie nach der entsprechenden Klasse suchen soll.
Nun habe ich folgende Überlegungen zusammen getragen:
Es gibt eine Funktion scan_dir(). Diese listet Dateien und Ordner innerhalb eines übergebenen Pfades aus.
Angenommen, ich würde die __autoload() Funktion so implementieren, das sie mit scan_dir() mein Root verzeichnis nach einer Datei absucht, die genauso heißt wie der übergebene Parameter für __autoload(), und mir diese dann entsprechend nachläd.
Also:
Ist dieser Lösungsansatz eher ungewöhnlich ?
Gibt es dort nicht vielleicht doch den einen oder anderen Harken ?
Ich frage mich nämlich gleichzeitig, wenn das alles so ohne weiteres funktioniert, warum hab ich eine solche Art von Lösung noch nirgendwo anders gesehen ?
So ich glaub das wars soweit auch. Vielen Dank für jeden Rat im Voraus
lasst euch bitte nicht von vorne rein von dem Titel des Themas abschrecken.
Das Thema __autoload() ist hier schon ziemlich oft besprochen worden, wobei es meist um das Verständnis der Funktion an sich ging.
Bei meinem aktuellen Problem geht es aber nicht um das Verständnis der Funktion, sondern viel mehr, einen Weg zu finden, diese optimal zu verwenden.
Mir ist bewusst, dass es in dieser Richtung schon einige Lösungsansätze gibt. Aber vorerst möchte ich euch mal schildern wie es zu meiner gleich gestellen Fragen kommt.
Also wie viele von euch wissen, ist die __autoload() - Funktion, eine Interzeptor - Funktion, die automatisch aufgerufen wird, sobald ein Objekt einer Klasse mit dem "new"-Operator instanziiert werden soll, diese allerdings noch nicht deklariert ist. __autoload() bekommt also den Namen der aufgerufenen ( noch nicht deklarierten ) Klasse als Parameter und kann nun die entsprechende Klasse nachladen.
Dieses Muster findet man bereits in einigen Frameworks wieder. Viele dieser Lösungen sind sehr ähnlich. So löst das Zend - Framework das Problem so, das die Klassennamen Unterstriche enthalten, diese später durch slashes ersetzt werden und somit einen gültigen Pfad zur entsprechenden Klasse darstellen.
So, oder so ähnlich würde es aussehen:
PHP-Code:
$frontcontroller = new Zend_Controller_Front();
Zend/Controller/Front.php
Habe ich beispielsweise eine Ordnerstruktur die so aussieht:
/user/admin.php
/user/teacher.php
PHP-Code:
$admin = new User_Admin();
$teacher = new User_Teacher();
Nach weiteren Überlegungen dachte ich man könnte es folgendermaßen schöner machen:
Eine Instanziierung der Klasse Admin (für dieses Beispiel) würde so aussehen:
PHP-Code:
$user = new UserAdmin();
genutzt werden kann.
Aber auch hier finde ich einige Punkte die mich Stören. Zum einen,
werden bei diesem Lösungsansatz die Klassenbezeichner im Code schwer leserlich, sobald die Ordnerstruktur zur entsprechenden Klasse mehr als 2 oder 3 Ordner betrifft.
So wird aus der Ordnerstruktur:
Db/Connection/MySql.php
PHP-Code:
$connection = new DbConnectionMysql();
die Zend - Konvention vorziehen, da aus dem oben genannten Pfad folgende Klassenbezeichnung entstehen würde:
PHP-Code:
$connection = new Db_Connection_MySql();
Ein weiterer Punkt der viele Probleme mit sich bringt, bei der Verwendung der Camel Case - Konvention ( ich nenne sie jetzt mal so ),
ist, dass die eigentlichen Dateinamen der Klassen auf nur einen ersten Großbuchstaben beschränkt sind.
Gut sichtbar ist dies in dem Beispiel von oben:
PHP-Code:
$connection = new DbConnectionMySql();
So nun hab ich viel erzählt.
Meine Fragestellung ist folgende:
Ich würde mir wünschen Klassen ganz normal nach ihrem wirklichen Bezeichner zu instanziieren.
Das bedeutet also sowas wie:
PHP-Code:
$user = new Admin();
Problem ist hier natürlich, das __autoload() nicht weiß, wo sie suchen muss. Dieses Problem gibt es in dem obigen Beispielen nicht.
Ich suche also nach einer Lösung, eine __autoload() Funktion zu implementieren, die mir allein anhand des Klassenbezeichners, den ich auch aufrufe, die Entsprechende Klasse nachäd.
Dies ist ja so ohne weiteres nicht möglich, wenn __autoload() nicht weiß, wo sie nach der entsprechenden Klasse suchen soll.
Nun habe ich folgende Überlegungen zusammen getragen:
Es gibt eine Funktion scan_dir(). Diese listet Dateien und Ordner innerhalb eines übergebenen Pfades aus.
Angenommen, ich würde die __autoload() Funktion so implementieren, das sie mit scan_dir() mein Root verzeichnis nach einer Datei absucht, die genauso heißt wie der übergebene Parameter für __autoload(), und mir diese dann entsprechend nachläd.
Also:
PHP-Code:
$user = new Admin();
// Funktion __autoload() würde im gesamten Ordnersystem (oder auch nur einige Bereiche), nach Admin.php suchen und diese nachladen.
Ist dieser Lösungsansatz eher ungewöhnlich ?
Gibt es dort nicht vielleicht doch den einen oder anderen Harken ?
Ich frage mich nämlich gleichzeitig, wenn das alles so ohne weiteres funktioniert, warum hab ich eine solche Art von Lösung noch nirgendwo anders gesehen ?
So ich glaub das wars soweit auch. Vielen Dank für jeden Rat im Voraus
Kommentar