Ich arbeite an einem Projekt mit folgender Dateistruktur:
index.php
|---lib
|--|lib|type|class_name.php
|--|lib|size|example_class.php
Ich möchte die Klassen class_name und example_class (benannt wie die Klassen PHP)) automatisch laden, damit die Klassen in index.php bereits instanziiert werden und ich Folgendes tun kann:
$class_name->getPrivateParam('name');
Ich habe im Internet nachgesehen, kann aber nicht die richtige Antwort finden - kann mir jemand helfen?
Danke für die Antworten. Lassen Sie mich mein Szenario erweitern. Ich versuche, ein WordPress Plugin zu schreiben, das in ein Projekt eingefügt werden kann, und zusätzliche Funktionen, die hinzugefügt werden, indem eine Klasse in einen Ordner "Funktionalität" zum Beispiel im Plugin abgelegt wird. Es wird nie eine geben 1000 Klassen, bei einem Push vielleicht 10?
Ich konnte eine Methode schreiben, um die Ordnerstruktur des 'lib'-Ordners zu durchlaufen, einschließlich jeder Klasse, die sie dann einer Variablen (des Klassennamens) zuordnet, hielt dies jedoch nicht für eine sehr effiziente Methode, sondern für eine solche Vielleicht scheint das der beste Weg zu sein, um das zu erreichen, was ich brauche?
Wenn Sie Klassen automatisch laden müssen - verwenden Sie die Konventionen für Namespaces und Klassennamen mit SPL-Autoload, um Zeit für das Refactoring zu sparen. Und natürlich müssen Sie jede Klasse als Objekt instanziieren. Vielen Dank.
Wie in diesem Thread: PHP Autoloading in Namespaces
Wenn Sie eine komplexe Problemumgehung wünschen, schauen Sie sich bitte die Autoload-Klasse von Symfony an: https://github.com/symfony/ClassLoader/blob/master/ClassLoader.php
Oder so (ich habe es in einem meiner Projekte gemacht):
<?
spl_autoload_register(function($className)
{
$namespace=str_replace("\\","/",__NAMESPACE__);
$className=str_replace("\\","/",$className);
$class=CORE_PATH."/classes/".(empty($namespace)?"":$namespace."/")."{$className}.class.php";
include_once($class);
});
?>
und dann können Sie Ihre Klasse wie folgt instanziieren:
<?
$example=new NS1\NS2\ExampleClass($exampleConstructParam);
?>
und das ist deine Klasse (gefunden in /NS1/NS2/ExampleClass.class.php):
<?
namespace NS1\NS2
{
class Symbols extends \DB\Table
{
public function __construct($param)
{
echo "hello!";
}
}
}
?>
Wenn Sie Zugriff auf die Befehlszeile haben, können Sie es mit composer in der classMap-Sektion mit so etwas versuchen:
{
"autoload": {
"classmap": ["yourpath/", "anotherpath/"]
}
}
dann musst du ein wordpress plugin aktivieren composer im wordpress cli: http: // wordpress .org/plugins/composer /
http://php.net/manual/de/function.spl-autoload-register.php
spl_autoload_register(function ($class) {
@require_once('lib/type/' . $class . '.php');
@require_once('lib/size/' . $class . '.php');
});
function __autoload($class_name) {
$class_name = strtolower($class_name);
$path = "{$class_name}.php";
if (file_exists($path)) {
require_once($path);
} else {
die("The file {$class_name}.php could not be found!");
}
}
PDATE:__autoload()
ist veraltet ab PHP 7.2
Ich habe hier ein Beispiel, das ich zum automatischen Laden und Initialisieren verwende.
Grundsätzlich eine bessere Version von spl_autoload_register, da nur versucht wird, die Klassendatei zu benötigen, wenn Sie die Klasse initialisieren.
Hier bekommt es automatisch jede Datei in Ihrem Klassenordner, benötigt die Dateien und initialisiert sie. Sie müssen lediglich der Klasse den gleichen Namen geben wie der Datei.
index.php
<?php
require_once __DIR__ . '/app/autoload.php';
$loader = new Loader(false);
User::dump(['hello' => 'test']);
autoload.php
<?php
class Loader
{
public static $library;
protected static $classPath = __DIR__ . "/classes/";
protected static $interfacePath = __DIR__ . "/classes/interfaces/";
public function __construct($requireInterface = true)
{
if(!isset(static::$library)) {
// Get all files inside the class folder
foreach(array_map('basename', glob(static::$classPath . "*.php", GLOB_BRACE)) as $classExt) {
// Make sure the class is not already declared
if(!in_array($classExt, get_declared_classes())) {
// Get rid of php extension easily without pathinfo
$classNoExt = substr($classExt, 0, -4);
$file = static::$path . $classExt;
if($requireInterface) {
// Get interface file
$interface = static::$interfacePath . $classExt;
// Check if interface file exists
if(!file_exists($interface)) {
// Throw exception
die("Unable to load interface file: " . $interface);
}
// Require interface
require_once $interface;
//Check if interface is set
if(!interface_exists("Interface" . $classNoExt)) {
// Throw exception
die("Unable to find interface: " . $interface);
}
}
// Require class
require_once $file;
// Check if class file exists
if(class_exists($classNoExt)) {
// Set class // class.container.php
static::$library[$classNoExt] = new $classNoExt();
} else {
// Throw error
die("Unable to load class: " . $classNoExt);
}
}
}
}
}
/*public function get($class)
{
return (in_array($class, get_declared_classes()) ? static::$library[$class] : die("Class <b>{$class}</b> doesn't exist."));
}*/
}
Sie können problemlos mit ein wenig Code umgehen, um auch Klassen in verschiedenen Ordnern zu benötigen.
Hoffentlich kann Ihnen das etwas nützen.
Mit diesem Autoloader können Sie ein für Namespaces geeignetes Autoloading festlegen.
<?php
spl_autoload_register(function($className) {
$file = __DIR__ . '\\' . $className . '.php';
$file = str_replace('\\', DIRECTORY_SEPARATOR, $file);
if (file_exists($file)) {
include $file;
}
});
Stellen Sie sicher, dass Sie den Speicherort der Klassendatei korrekt angeben.