| 選項 | 說明 |
| OR REPLACE | 視圖存在時覆蓋,避免先 DROP 再 CREATE |
| ALGORITHM=MERGE | 將視圖查詢合併到外層查詢(效能最佳,有限制) |
| ALGORITHM=TEMPTABLE | 先建立臨時表再查詢(支援所有查詢,效能較差) |
| WITH CHECK OPTION | 防止透過視圖插入/更新不符合視圖 WHERE 條件的行 |
| CASCADED/LOCAL | 巢狀視圖檢查範圍 |
實戰建立範例
-- 1. 簡單視圖:隱藏敏感欄位
CREATE VIEW v_employee_public AS
SELECT id, first_name, last_name, city, department
FROM employee
WHERE status = 'active';
-- 2. 複雜聚合視圖:部門薪資統計
CREATE VIEW v_dept_salary AS
SELECT department,
COUNT(*) AS emp_count,
AVG(salary) AS avg_salary,
MAX(salary) AS max_salary
FROM employee
GROUP BY department;
-- 3. 帶檢查選項:只能透過視圖操作台北員工
CREATE VIEW v_taipei_emp AS
SELECT * FROM employee WHERE city = 'Taipei'
WITH CHECK OPTION;
-- 4. 指定演算法
CREATE ALGORITHM=MERGE VIEW v_simple AS
SELECT id, name FROM products WHERE price > 100;
視圖操作指令
修改視圖
-- 完全替換定義
CREATE OR REPLACE VIEW v_employee_public AS
SELECT id, first_name, last_name, city, department, hire_date
FROM employee WHERE status = 'active';
-- 或使用 ALTER(語法相同)
ALTER VIEW v_employee_public AS
SELECT ...;
刪除視圖
DROP VIEW [IF EXISTS] view_name [, view_name2 ...];
查看視圖定義
SHOW CREATE VIEW view_name;
-- 或
SELECT * FROM INFORMATION_SCHEMA.VIEWS WHERE TABLE_NAME = 'view_name';
列出所有視圖
SHOW FULL TABLES WHERE TABLE_TYPE = 'VIEW';
-- 或
SELECT TABLE_NAME FROM INFORMATION_SCHEMA.VIEWS WHERE TABLE_SCHEMA = 'db_name';
視圖可更新性條件
視圖可更新需同時滿足:
- 單一基礎表(無 JOIN、UNION、子查詢)
- 無聚合函數、GROUP BY、DISTINCT
- SELECT 清單為直接欄位引用(非運算式)
- 無
WITH CHECK OPTION 衝突
實用技巧: 即使視圖不可直接更新,可建立 INSTEAD OF 觸發器(MySQL 不支援)或在應用層拆解更新邏輯。
權限控制
| 操作 | 所需權限 |
| 建立視圖 | CREATE VIEW + 基礎表 SELECT |
| 查詢視圖 | 視圖 SELECT(不需基礎表權限) |
| 修改視圖 | CREATE VIEW + DROP 權限(實為重建) |
| 刪除視圖 | DROP 權限 |
PHP 應用範例
<?php
$mysqli = new mysqli("localhost", "root", "123456", "xiaoqiangdb");
$sql = "SELECT * FROM v_employee_public ORDER BY hire_date";
$result = $mysqli->query($sql);
echo '<table border="1" align="center">';
while ($row = $result->fetch_assoc()) {
echo '<tr>';
foreach ($row as $col) {
echo '<td>' . htmlspecialchars($col) . '</td>';
}
echo '</tr>';
}
echo '</table>';
$mysqli->close();
?>
最佳實踐建議
- 視圖命名規範:
v_ 前綴 + 業務名稱
- 複雜視圖加註釋:
COMMENT = '部門薪資統計,每日更新'
- 定期檢查視圖效能:
EXPLAIN SELECT * FROM view_name
- 避免巢狀視圖過深(>3層),維護困難且效能難預測
- 敏感資料務必透過視圖隔離,不直接授予基礎表權限
- 上一篇文章: MySQL "Illegal mix of collations" 編碼衝突完整解決方案
- 下一篇文章: PHP MySQLi 預處理語句兩大實戰範例(防注入、高效能)
Copyright ©
程式碼之家 All Rights Reserved