PHP不用递归遍历目录下所有文件的代码


Posted in PHP onJuly 04, 2014

实现代码:

/**
 * PHP 非递归实现查询该目录下所有文件
 * @param unknown $dir
 * @return multitype:|multitype:string
 */
function scanfiles($dir) {
 if (! is_dir ( $dir ))
 return array ();
 
 // 兼容各操作系统
 $dir = rtrim ( str_replace ( '\\', '/', $dir ), '/' ) . '/';
 
 // 栈,默认值为传入的目录
 $dirs = array ( $dir );
 
 // 放置所有文件的容器
 $rt = array ();
 
 do {
 // 弹栈
 $dir = array_pop ( $dirs );
 
 // 扫描该目录
 $tmp = scandir ( $dir );
 
 foreach ( $tmp as $f ) {
  // 过滤. ..
  if ($f == '.' || $f == '..')
  continue;
  
  // 组合当前绝对路径
  $path = $dir . $f;
  
  
  // 如果是目录,压栈。
  if (is_dir ( $path )) {
  array_push ( $dirs, $path . '/' );
  } else if (is_file ( $path )) { // 如果是文件,放入容器中
  $rt [] = $path;
  }
 }
 
 } while ( $dirs ); // 直到栈中没有目录
 
 return $rt;
}

附另一篇:不用递归遍历目录下的文件

如果要遍历某个目录下的所有文件(包括子目录),最首先想到的思路就是用递归:先处理当前目录,再处理当前目录下的子目录。不用递归可不可以呢?以前学数据结构的时候看到过,递归其实是利用堆栈来实现的,递归的特点就是不断的调用自身,最后一次的调用是最先执行完的,倒数第二次调用是其次执行完的,依次类推,最初的调用是最后执行完的。如果理解了递归的原理,其实就可以把所有用递归的实现转化为非递归的实现。

用非递归方式遍历某个目录下的所有文件,思路主要分三步:

1. 创建一个数组,将要遍历的这个目录放入;(其实就是创建了一个栈)
2. 循环处理这个数组,循环结束的条件是数组为空;
3. 每次循环,处理数组中的一个元素,并将元素删除,如果这个元素是目录,则将目录下所有的子元素加入数组;

按照这种思路写出的代码如下:

/**
 * 遍历某个目录下的所有文件
 * @param string $dir
 */
function scanAll($dir)
{
  $list = array();
  $list[] = $dir;

  while (count($list) > 0)
  {
    //弹出数组最后一个元素
    $file = array_pop($list);

    //处理当前文件
    echo $file."\r\n";

    //如果是目录
    if (is_dir($file))
    {
      $children = scandir($file);
      foreach ($children as $child)
      {
        if ($child !== '.' && $child !== '..')
        {
          $list[] = $file.'/'.$child;
        }
      }
    }
  }
}

这里我并没有认为递归有多大的缺点,事实上很多情况下,用递归来设计还是非常简洁可读的,至于效率问题,除非在递归深度特别大的时候,才会有影响。

以下是用递归的实现,作为对比:

/**
 * 遍历某个目录下的所有文件(递归实现)
 * @param string $dir
 */
function scanAll2($dir)
{
  echo $dir."\r\n";

  if (is_dir($dir))
  {
    $children = scandir($dir);
    foreach ($children as $child)
    {
      if ($child !== '.' && $child !== '..')
      {
        scanAll2($dir.'/'.$child);
      }
    }
  }
}

运行发现,两个函数的结果略有不同,主要表现在打印的顺序上。函数一运行结果的顺序是倒着的,是因为压栈的顺序正好和scandir出来的顺序相反了,可以将第21行改一下:

$children = array_reverse(scandir($file));

这样出来结果就完全相同了。

PHP 相关文章推荐
php-accelerator网站加速PHP缓冲的方法
Jul 30 PHP
mysql5的sql文件导入到mysql4的方法
Oct 19 PHP
不支持fsockopen但支持culr环境下下ucenter与modoer通讯问题
Aug 12 PHP
PHP正则表达式之定界符和原子介绍
Oct 05 PHP
PHP+Ajax检测用户名或邮件注册时是否已经存在实例教程
Aug 23 PHP
php实现Session存储到Redis
Nov 11 PHP
Laravel路由设定和子路由设定实例分析
Mar 30 PHP
thinkphp制作404跳转页的简单实现方法
Sep 22 PHP
PHP错误和异常处理功能模块示例
Nov 12 PHP
PHP实现登陆并抓取微信列表中最新一组微信消息的方法
Jul 10 PHP
PHP以json或xml格式返回请求数据的方法
May 31 PHP
php使用mysqli和pdo扩展,测试对比连接mysql数据库的效率完整示例
May 09 PHP
对于ThinkPHP框架早期版本的一个SQL注入漏洞详细分析
Jul 04 #PHP
PHP+Memcache实现wordpress访问总数统计(非插件)
Jul 04 #PHP
php+memcache实现的网站在线人数统计代码
Jul 04 #PHP
PHP轻量级数据库操作类Medoo增加、删除、修改、查询例子
Jul 04 #PHP
CodeIgniter安全相关设置汇总
Jul 03 #PHP
php使用pack处理二进制文件的方法
Jul 03 #PHP
PHP源码分析之变量的存储过程分解
Jul 03 #PHP
You might like
一个颜色轮换的简单例子
2006/10/09 PHP
php中动态修改ini配置
2014/10/14 PHP
详解PHP匿名函数与注意事项
2016/03/29 PHP
PHP实现支持加盐的图片加密解密
2016/09/09 PHP
YII2自动登录Cookie总是失效的解决方法
2017/06/28 PHP
js表数据排序 sort table data
2009/02/18 Javascript
JavaScript中变量提升 Hoisting
2012/07/03 Javascript
javascript实现div的显示和隐藏的小例子
2013/06/25 Javascript
Jquery实现搜索框提示功能示例代码
2013/08/13 Javascript
自定义ExtJS控件之下拉树和下拉表格附源码
2013/10/15 Javascript
JavaScript 实现打印,打印预览,打印设置
2014/12/30 Javascript
jQuery中DOM树操作之使用反向插入方法实例分析
2015/01/23 Javascript
js制作简易年历完整实例
2015/01/28 Javascript
JavaScript操作URL的相关内容集锦
2015/10/29 Javascript
javascript实现checkbox复选框实例代码
2016/01/10 Javascript
Jquery+ajax+JAVA(servlet)实现下拉菜单异步取值
2016/03/23 Javascript
BootStrap 附加导航组件
2016/07/22 Javascript
AngularJS基础 ng-keydown 指令简单示例
2016/08/02 Javascript
JavaScript阻止表单提交方法(附代码)
2017/08/15 Javascript
Node.js中使用mongoose操作mongodb数据库的方法
2017/09/12 Javascript
Vue实现带进度条的文件拖动上传功能
2018/02/23 Javascript
微信小程序websocket聊天室的实现示例代码
2019/02/12 Javascript
Vue中的this.$options.data()和this.$data用法说明
2020/07/26 Javascript
Python二元赋值实用技巧解析
2019/10/25 Python
python+selenium+Chrome options参数的使用
2020/03/18 Python
python 带时区的日期格式化操作
2020/10/23 Python
html5关于外链嵌入页面通信问题(postMessage解决跨域通信)
2020/07/20 HTML / CSS
Elemis美国官网:英国的第一豪华护肤品牌
2018/03/15 全球购物
编程用JAVA解析XML的方式
2013/07/07 面试题
工程造价管理专业大专生求职信
2013/10/06 职场文书
红领巾心向党广播稿
2014/01/19 职场文书
教堂婚礼主持词
2014/03/14 职场文书
工程质量承诺书
2014/03/27 职场文书
结婚保证书范文
2014/04/29 职场文书
挂职个人工作总结
2015/03/05 职场文书
优秀团员自我评价
2015/03/10 职场文书