首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> 網頁程式設計 >> PHP 程式設計 >> PHP 綜合知識

PHP 遞迴建立多層級目錄:makedir() 函數完整實作

     編輯:PHP 綜合知識

PHP mkdir() 預設不支援遞迴建立多層目錄(PHP 5.0+ 已支援 recursive 參數),但理解手動實作邏輯有助於處理特殊權限、錯誤處理等進階需求。

手動實作版(相容舊版 PHP)

<?php
/**
 * 遞迴建立多層目錄
 * @param string $dir  目標路徑(如 a/b/c/d)
 * @param int    $mode 權限(預設 0700)
 * @return string|false 成功回傳路徑,失敗 false
 */
function makedir($dir, $mode = 0700) {
    // 正規化路徑分隔符
    $dir = str_replace('\\', '/', $dir);
    $dir = rtrim($dir, '/');

    if (is_dir($dir)) return $dir; // 已存在

    $parts = explode('/', $dir);
    $current = '';

    foreach ($parts as $part) {
        $current .= $part . '/';
        if (!is_dir($current)) {
            if (!@mkdir($current, $mode)) {
                trigger_error("建立目錄失敗: $current", E_USER_WARNING);
                return false;
            }
            @chmod($current, $mode); // 確保權限
        }
    }
    return $dir;
}

// 使用範例
makedir('data/cache/user/123/profile');
makedir('../uploads/2024/12/25', 0755);

現代 PHP 內建寫法(PHP 5.0+)

// 單行搞定,支援遞迴
mkdir('data/cache/user/123/profile', 0755, true);
// 第三參數 true = recursive

進階:含錯誤處理與回報的封裝類

class Directory {
    public static function make($path, $mode = 0755) {
        $path = rtrim(str_replace('\\', '/', $path), '/');
        
        if (is_dir($path)) return ['success' => true, 'path' => $path, 'created' => false];
        
        $created = [];
        $parts = explode('/', $path);
        $current = '';
        
        foreach ($parts as $part) {
            $current .= $part . '/';
            if (!is_dir($current)) {
                $result = @mkdir($current, $mode);
                if (!$result) {
                    return ['success' => false, 'path' => $current, 'error' => error_get_last()];
                }
                @chmod($current, $mode);
                $created[] = $current;
            }
        }
        return ['success' => true, 'path' => $path, 'created' => $created];
    }
}

// 使用
$result = Directory::make('var/log/app/2024/12');
if ($result['success']) {
    echo "建立成功,新建目錄: " . implode(', ', $result['created']);
} else {
    echo "失敗於 {$result['path']}: {$result['error']['message']}";
}

關鍵細節對照

細節手動實作內建 mkdir(recursive)
PHP 版本需求全版本5.0+
權限控制逐層 chmod() 可精細控制僅最終目錄套用 mode,父目錄受 umask 影響
錯誤處理可自訂每層失敗行為整體失敗,無法知曉哪層出問題
效能多次系統呼叫內核優化,單次呼叫
競態條件需自行處理內核原子性較好

最佳實踐建議

  • 現代專案:直接用 mkdir($path, 0755, true)
  • 需精細權限/審計:使用封裝類逐層建立並記錄
  • 高併發環境:考慮 flock() 鎖定或資料庫協調
  • Windows 相容:路徑統一用 /,PHP 內部自動轉換

理解遞迴建目錄邏輯,能在權限管理、錯誤診斷、跨平台相容等進階場景遊刃有餘。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved