當前位置: 首頁> 最新文章列表> 如何處理PDOStatement::fetchObject 中的日期時間格式

如何處理PDOStatement::fetchObject 中的日期時間格式

gitbox 2025-05-12

在使用PHP 的PDO 操作數據庫時, PDOStatement::fetchObject()方法非常方便,它可以將查詢結果直接映射為一個對象。然而,當數據庫字段中包含(如DATETIMETIMESTAMP類型)時,直接使用fetchObject可能會遇到一些問題,比如日期字段被當作普通字符串處理,導致後續格式化和比較變得麻煩。

本文將講解如何在使用fetchObject時,正確地處理這些日期時間字段,並給出實用示例。

問題背景

假設有一個用戶表users ,結構如下:

 CREATE TABLE users (
    id INT PRIMARY KEY AUTO_INCREMENT,
    name VARCHAR(255) NOT NULL,
    created_at DATETIME NOT NULL
);

插入一條數據:

 INSERT INTO users (name, created_at) VALUES ('Alice', '2025-04-27 14:30:00');

fetchObject獲取數據:

 <?php
$pdo = new PDO('mysql:host=localhost;dbname=test', 'username', 'password');
$stmt = $pdo->query('SELECT * FROM users WHERE id = 1');
$user = $stmt->fetchObject();

echo $user->created_at;
?>

輸出的是一段普通字符串

 2025-04-27 14:30:00

如果想要對created_at進行時間加減、格式化等操作,就不得不手動用DateTime類轉換,非常不優雅。

正確處理日期時間字段的方法

有兩種常見方式來優雅地處理:

方法一:手動轉換字段

在拿到對像後,立即將日期字段轉成DateTime對象。

 <?php
$pdo = new PDO('mysql:host=localhost;dbname=test', 'username', 'password');
$stmt = $pdo->query('SELECT * FROM users WHERE id = 1');
$user = $stmt->fetchObject();

if ($user && isset($user->created_at)) {
    $user->created_at = new DateTime($user->created_at);
}

// 現在可以直接使用 DateTime 方法
echo $user->created_at->format('Y年m月d天 H:i:s');
?>

雖然這種方式簡單,但每次都要手動轉換,如果表結構複雜或者字段多,維護成本會增加。

方法二:使用自定義實體類(推薦)

創建一個實體類,定義好對應的屬性類型,並在構造函數中自動處理日期時間。

 <?php
class User
{
    public int $id;
    public string $name;
    public DateTime $created_at;

    public function __construct()
    {
        // 需要將原本的字符串 created_at 轉成 DateTime 對象
        if (is_string($this->created_at)) {
            $this->created_at = new DateTime($this->created_at);
        }
    }
}
?>

使用fetchObject時指定類名:

 <?php
$pdo = new PDO('mysql:host=localhost;dbname=test', 'username', 'password');
$stmt = $pdo->query('SELECT * FROM users WHERE id = 1');
$user = $stmt->fetchObject(User::class);

echo $user->created_at->format('Y-m-d H:i:s');
?>

這樣做的好處是:

  • 代碼更清晰

  • 避免遺漏字段處理

  • 對象結構更規範,方便IDE 自動補全

  • 適合更大型的項目或長期維護

注意事項

如果你的PHP 版本支持,可以結合屬性類型聲明,例如PHP 8.0 引入的constructor property promotion,進一步簡化實體類寫法。

同時,確保數據庫返回的字段格式始終符合ISO 標準( YYYY-MM-DD HH:MM:SS ),以免DateTime解析失敗。

小結

使用PDOStatement::fetchObject()時,直接返回的日期時間字段是字符串。如果需要優雅處理,建議:

  • 小項目可在取出後手動轉換為DateTime

  • 大項目或規範開發中,強烈推薦使用自定義實體類

通過合理設計實體類,可以極大提升代碼的健壯性和可維護性。

如果你想了解更多關於PDO 使用技巧,可以參考官方文檔