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

PHP 正則表達式提取與替換 img 標籤屬性完整指南

     編輯:PHP 相關知識

處理富文本內容時,常需從 <img> 標籤提取 src、width、height,或批次修改圖片路徑、移除尺寸屬性。本文提供實戰正則模式與 preg_replace 替換技巧。

一、測試字串

<?php
$str = '<center><img src="/uploads/images/20100516000.jpg" height="120" width="120"><br />PHP正則提取或更改圖片img標籤中的任意屬性</center>';
?>

二、提取屬性

1. 取完整 <img> 標籤

preg_match('/<\s*img\s+[^>]*?src\s*=\s*([\'"])(.*?)\1[^>]*?\/?\s*>/i', $str, $match);
echo $match[0]; // 完整標籤

2. 取 width

preg_match('/<img.+?(width\s*=\s*[\'"]?\d*[\'"]?).+?>/i', $str, $match);
echo $match[1]; // width="120"

3. 取 height

preg_match('/<img.+?(height\s*=\s*[\'"]?\d*[\'"]?).+?>/i', $str, $match);
echo $match[1]; // height="120"

4. 取 src(支援多種圖片格式)

preg_match('/<img.+?src\s*=\s*[\'"]?(.+?\.(?:jpg|gif|bmp|png))[\'"]?.+?>/i', $str, $match);
echo $match[1]; // /uploads/images/20100516000.jpg

三、替換屬性

1. 修改 src 路徑(在 images 前插入 uc/)

// 將 src="/uploads/images/xxx.jpg" → src="/uploads/uc/images/xxx.jpg"
echo preg_replace(
    '/(<img.+?src\s*=\s*[\'"]?.+?)(images\/)(.+?\.(?:jpg|gif|bmp|png)[\'"]?.+?>)/i',
    '${1}uc/images/${3}',
    $str
);

2. 修改 src 並移除 width/height

// 保留 img 標籤與新 src,刪除其餘屬性
echo preg_replace(
    '/(<img).+?(src\s*=\s*[\'"]?.+?)images\/(.+?\.(?:jpg|gif|bmp|png)[\'"]?).+?>/i',
    '${1} ${2}uc/images/${3}>',
    $str
);
// 結果:

四、更健壯的通用函數:DOMDocument 解析(推薦生產使用)

正則處理 HTML 易受屬性順序、換行、單雙引號、巢狀標籤影響。PHP 內建 DOMDocument 更可靠:

<?php
function extractImgAttributes($html) {
    $dom = new DOMDocument();
    libxml_use_internal_errors(true);
    $dom->loadHTML('' . $html); // 修正編碼警告
    libxml_clear_errors();

    $images = [];
    foreach ($dom->getElementsByTagName('img') as $img) {
        $attr = [];
        foreach ($img->attributes as $name => $node) {
            $attr[$name] = $node->value;
        }
        $images[] = $attr;
    }
    return $images;
}

function replaceImgSrc($html, callable $callback) {
    $dom = new DOMDocument();
    libxml_use_internal_errors(true);
    $dom->loadHTML('' . $html);
    libxml_clear_errors();

    foreach ($dom->getElementsByTagName('img') as $img) {
        if ($img->hasAttribute('src')) {
            $newSrc = $callback($img->getAttribute('src'), $img);
            if ($newSrc !== null) $img->setAttribute('src', $newSrc);
        }
    }

    // 取得 body 內容(loadHTML 會補全 html/body)
    $body = $dom->getElementsByTagName('body')->item(0);
    $result = '';
    foreach ($body->childNodes as $node) {
        $result .= $dom->saveHTML($node);
    }
    return $result;
}

// 使用範例:所有圖片路徑加上 CDN 前綴
$newHtml = replaceImgSrc($str, function($src) {
    if (strpos($src, 'http') !== 0) {
        return 'https://cdn.example.com' . $src;
    }
    return $src;
});
?>

五、正則 vs DOMDocument 選擇指南

場景推薦方式理由
簡單、固定格式、一次性腳本正則代碼短、無依賴、執行快
使用者輸入、富文本編輯器輸出、結構複雜DOMDocument正確解析巢狀、屬性順序、實體編碼
需修改多個屬性、刪除標籤、包裹標籤DOMDocument物件模型操作直觀、不易破壞結構
超大 HTML(>10MB)、記憶體受限XMLReader / 串流解析DOM 會將整棵樹載入記憶體

六、常見正則陷阱與修正

  • 貪婪匹配吃掉多個標籤:使用非貪婪 .*? 或排除字元集 [^>]*。
  • 屬性值含單引號/雙引號混用:用 [\'"] 匹配並反向引用 \1。
  • 跨行標籤:加 s 修飾符 /.../is 讓 . 匹配換行。
  • 自我閉合 <img ... />:模式加 \/? 兼容。
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved