PaulH
PaulH

Reputation: 7853

fastest way to locate directories containing a specific item

I have a PHP 5.3.4 application running on Windows XP SP3 where I need to index the contents of a directory on a remote PC. The largest directory I'm indexing contains around 18,000 items.

This call would locate items like \\somepc.mycorp.com\foo\mydir\bar\zoo.zip.

// look in all the directories in \\somepc.mycorp.com\foo for directories containing a file \bar\zoo.zip
$item_list = GetFileList('\\\\somepc.mycorp.com\\foo', '\\bar\\zoo.zip');

It is implemented as:

function GetFileList($base_dir, $path_mask)
{
    $result= array();
    if ($handle = opendir($base_dir)) 
    {
        while (false !== ($entry = readdir($handle))) 
        {
            // only add items that match the mask we're looking for
            if ($entry != "." &&
                $entry != ".." && 
                file_exists($base_dir.'\\$entry\\$path_mask'))
            {
                array_push($result, $entry);
            }
        }

        closedir($handle);
    }
    return $result;
}

Unfortunately, for the largest directory structures, this operation can take over an hour. If I remove the filter and just insert every item seen in to the array, it will finish in a few seconds.

Is there a faster way to accomplish this?

Upvotes: 2

Views: 65

Answers (1)

Jonathan Rich
Jonathan Rich

Reputation: 1738

I hate to pull this card, but what you're doing can be completed much faster using bash or even windows scripting - PHP is probably not the right tool for the job here. A system call (even from within PHP) to dir /s /b or find will get you a list of all files that exist, and then you can iterate over those strings with PHP much more quickly than checking to see if a file exists in every directory.

I would do this in bash like this (because I'm lazy and don't know the proper find syntax):

find | grep '/bar/zoo.zip'

I don't know the appropriate windows shell command (because I have WinGnu32 grep installed on my machine), so I can't help you there.

Edit:

I did a bit of fudging around and found the Windows equivalent of the above command:

dir /s /b | find "/bar/zoo.zip"

Upvotes: 3

Related Questions