Estoy tratando de iterar sobre un directorio que contiene una gran cantidad de archivos PHP y detectar qué clases están definidas en cada archivo.Combinando resultados iterativos recursivos: niños con padres
considerar lo siguiente:
$php_files_and_content = new PhpFileAndContentIterator($dir);
foreach($php_files_and_content as $filepath => $sourceCode) {
// echo $filepath, $sourceCode
}
El $php_files_and_content
variable de anterior representa un iterador donde la clave es la ruta de archivo, y el contenido es el código fuente del archivo (como si eso no era evidente a partir del ejemplo)
Ésta se incluye a continuación, en otro iterador que coincidirá con todas las clases definidas en el código fuente, Ala:
class DefinedClassDetector extends FilterIterator implements RecursiveIterator {
public function accept() {
return $this->hasChildren();
}
public function hasChildren() {
$classes = getDefinedClasses($this->current());
return !empty($classes);
}
public function getChildren() {
return new RecursiveArrayIterator(getDefinedClasses($this->current()));
}
}
$defined_classes = new RecursiveIteratorIterator(new DefinedClassDetector($php_files_and_content));
foreach($defined_classes as $index => $class) {
// print "$index => $class"; outputs:
// 0 => Class A
// 1 => Class B
// 0 => Class C
}
La razón por la $index
no es secuencial numérico se debe a 'Clase C' se define en el segundo archivo de código fuente, y por lo tanto, la matriz devuelta comienza desde el índice 0 nuevamente. Esto se conserva en RecursiveIteratorIterator porque cada conjunto de resultados representa un iterador separado (y, por lo tanto, pares clave/valor).
De todos modos, lo que estoy tratando de hacer ahora es encontrar la mejor manera de combinar estos, de tal manera que cuando iterar sobre el nuevo iterador, puedo conseguir la clave es el nombre de la clase (de la $defined_classes
iterador) y el valor es la ruta del archivo original, ala:
foreach($classes_and_paths as $filepath => $class) {
// print "$class => $filepath"; outputs
// Class A => file1.php
// Class B => file1.php
// Class C => file2.php
}
Y ahí es donde estoy estancado hasta ahora.
Por el momento, la única solución que se viene a la mente es crear un nuevo RecursiveIterator, que anula el método actual() para devolver la clave externa del iterador() (que sería el original del archivo) y la tecla () método para devolver el valor del iterador actual(). Pero no estoy a favor de esta solución porque:
- Suena complejo (lo que significa que el código se verá horrible y no va a ser intuitivo
- Las reglas de negocio son difíciles codificados dentro de la clase, mientras que yo le gustaría definir algunos iteradores genéricos y poder combinarlos de tal manera de producir el resultado deseado.
Cualquier idea o sugerencia agradecido recibimos.
también me di cuenta de que hay mucho más rápido, más eficiente formas de hacer esto, pero th También es un ejercicio de uso de Iterators para mí mismo y también un ejercicio para promover la reutilización de código, por lo que cualquier iterador nuevo que deba escribirse debe ser lo más mínimo posible e intentar aprovechar la funcionalidad existente.
Gracias
+1 para subir la barra y usar OOP en PHP –