Nasıl sadece bir PHP Iterasyon ile Klasörler seçilen edersiniz?

4 Cevap php

Ben bugüne kadar bu listelemek için php ve html dosyaları bulmak için PHP recursive dizin yineleyici kullanmaya çalışıyorum. Aşağıdaki gibi kullanılan kod:

    	$filelist = array();
	$iterator = new RecursiveDirectoryIterator( $this->_jrootpath );
	foreach(new RecursiveIteratorIterator($iterator) as $file) {
		if ( !$file->isDir() ) {
			if ( preg_match( "/.(html|htm|php)$/", $file->getFilename() ) ) {
				$filelist[$file->getPathname()] = $file->getMTime();
			}
		}
	}
	arsort($filelist);
	foreach ($filelist as $key => $val) {
		$resultoutput .= '			<tr>
										<td class="filepath">'.$key.'</td>
										<td class="filedate">'.date("d-m-Y H:i:s",$val).'</td>
									</tr>';
	}

Yukarıdaki eserler, ama ben belirli klasörlere yineleme kısıtlamak gerekir. Bu script beklediğim bir üst klasöre başlayacak (diğer bir deyişle, bir Joomla kurulum standart klasörleri) 'yönetici', 'bileşenleri', 'modüller', 'eklentileri' ve 'şablonlar' gibi bazı özel alt klasörler. Ben de 'index.php' gibi, üst klasörde birkaç dosya bekliyoruz. Bu dosya ve klasörleri (ana klasör kendisi benim kod tarafından iterated eğer ben emin değilim bu yazı, açıkçası!) Iterated edilmelidir. Ancak, ana klasör de iterated olmamalı, diğer alt klasörler içeren mümkündür. Bu alt veya 'MySub' ve 'myaddon.com' örneğin adını addon etki için alt klasörler olabilir. Ben normal bir Joomla kurulum klasörler dışında herhangi bir klasör atlamak isteyen iki nedeni vardır. Bir diğer klasörlerdeki dosyaları hakkında bilmeniz gereken kalmamasıdır. Ayrıca, tüm klasörleri yineleme 500 hata sayfaları olsun o kadar çok zaman ve kaynak alabilir.

Benim soru en doğru klasörler dışında ve yineleme dahil olduğundan emin olmak için benim kodunu değiştirmek istiyorsunuz nasıl? Ben bir dizinin adı denetleyerek web etrafında yineleyici örneklerini gördük, ama ben sadece ebeveyn / secondlevel / noneedtocheck gibi bir yol sadece en üst düzey alt klasör anlam ikinci düzey klasör adlarını (kontrol etmek gerekir, çünkü bu, beni yeterince yardımcı olmuyor / file.php).

4 Cevap

no no! YOu want something like:

<?php
class FilteredRecursiveDirectoryIterator extends FilterIterator
{   
    public function __construct($path)
    {
        parent::__construct(new RecursiveDirectoryIterator($path));
    }
    public function accept()
    {
        if($this->current()->isFile() and in_array($this->getExtention(), array('html', 'php')))
            return true;

        return false;
    }

    private function getExtention()
    {
        return end(explode('.', $this->current()->getFilename()));
    }
}

accept () yöntemi, sizin için tüm filtreleme yapar nerede. Ben bu test değil ama iyi gitmek eminim ;)

Bir işlevi yineleyici koyarak ben sonuç dizi oluşturmak için dahil edilecek bilinen klasörler için tekrar tekrar kullanabilirsiniz: Ben aşağıda denemek için gidiyorum. Hala bir gün daha zarif benim yöntemi iç içe bir fonksiyonu olmadan PHP iteratörler bir çözüm bulmak umuyoruz.

	$filelist = array();
	$filelist[$this->_jrootpath.DS.'index.php'] = date("d-m-Y H:i:s",filemtime($this->_jrootpath.DS.'index.php'));
	$filelist[$this->_jrootpath.DS.'index2.php'] = date("d-m-Y H:i:s",filemtime($this->_jrootpath.DS.'index2.php'));
	$joomlafolders = array( $this->_jrootpath.DS.'administrator', $this->_jrootpath.DS.'cache', $this->_jrootpath.DS.'components', $this->_jrootpath.DS.'images', $this->_jrootpath.DS.'includes', $this->_jrootpath.DS.'language', $this->_jrootpath.DS.'libraries', $this->_jrootpath.DS.'logs', $this->_jrootpath.DS.'media', $this->_jrootpath.DS.'modules', $this->_jrootpath.DS.'plugins', $this->_jrootpath.DS.'templates', $this->_jrootpath.DS.'tmp', $this->_jrootpath.DS.'xmlrpc' );
	foreach ( $joomlafolders as $folder ) {
		$iterator = new RecursiveDirectoryIterator( $folder );
		foreach(new RecursiveIteratorIterator($iterator) as $file) {
			if ( !$file->isDir() ) {
				if ( preg_match( "/.(html|htm|php)$/", $file->getFilename() ) ) {
					$filelist[$file->getPathname()] = $file->getMTime();
				}
			}
		}
	}
	arsort($filelist);
	foreach ($filelist as $key => $val) {
		$resultoutput .= '			<tr>
										<td class="filepath">'.$key.'</td>
										<td class="filedate">'.date("d-m-Y H:i:s",$val).'</td>
									</tr>';
	}

Sen RecursiveRegexIterator kullanarak deneyebilirsiniz.

EDIT Bu RecursiveRegexIterator kullanarak örnek:

$filelist = array();
$iterator = new RecursiveDirectoryIterator( $this->_jrootpath );
foreach(new RecursiveRegexIterator($iterator, '/\.(html|htm|php)$/') as $file) {
    if ( !$file->isDir() ) {
        $filelist[$file->getPathname()] = $file->getMTime();
    }
}
arsort($filelist);
foreach ($filelist as $key => $val) {
    $resultoutput .= '                      <tr>
                                                                            <td class="filepath">'.$key.'</td>
                                                                            <td class="filedate">'.date("d-m-Y H:i:s",$val).'</td>
                                                                    </tr>';
}

Arada, $resultoutput henüz oluşturulmuş değil gibi görünüyor. Bu durumda, bir yerde boş bir dize olarak oluşturmanız gerekir ...

EDIT2: Üzgünüz, bu gerçekten soruya cevap vermez. Nedense ben bu özyinelemeli şeyler hakkında sadece düşündüm. Bu dosyalar üzerinde döngü için sadece bir daha zarif bir çözümdür, ama üzgünüm, sorunu çözmüyor. Muhtemelen diğer yanıtları biri ile birleştirmek gerekir.

Genellikle RecursiveDirectoryIterator olarak "tekrarlamasinda" çözmek için RecursiveIteratorIterator kullanın. A RecursiveIteratorIterator sadece basit bir Iterator Eğer zaten aşina olabilecek diğer gibi kullanılabilir. Bu da beraberinde FilterIterator kullanımını da içerir. PHP 5.4 o (CallbackIterator yeni) benziyor

<?php
$directories = new CallbackIterator(
    new RecursiveIteratorIterator(
        new RecursiveDirectoryIterator('path/to/directory')
    ),
    function($current) {
        return $current->isDir();
    }
);

foreach ($directories as $directory) {
    ...
}

PHP <5.4 için kendinizi CallbackIterator uygulamak gerekir

<?php
class CallbackIterator extends FilterIterator
{
    private $callback;

    public function __construct(Traversable $iterator, $callback)
    {
        $this->callback = $callback;
    }

    public function accept()
    {
        return call_user_func($this->callback, $this->current());
    }
}