Php 使用pdo将NULL插入数据库

Php 使用pdo将NULL插入数据库,php,database,pdo,Php,Database,Pdo,在我正在使用的数据库中,有一个名为“packets”的表,在这个表中有“id”、“userid”等列和一个名为“usage”的列(我知道这是一个糟糕的名称选择,因为usage是一个保留字,但遗憾的是我可能不会更改表中的任何内容),该列的类型是带有3个值的enum(“教育”、“学习”和“学习”)“高级培训”),默认值为“教育”,该值可以为空 我编写了一个带有getter/setter的类包,比如set_usage($usage)/get_usage(),以及一个用于使用pdo访问数据库的类包: c

在我正在使用的数据库中,有一个名为“packets”的表,在这个表中有“id”、“userid”等列和一个名为“usage”的列(我知道这是一个糟糕的名称选择,因为usage是一个保留字,但遗憾的是我可能不会更改表中的任何内容),该列的类型是带有3个值的enum(“教育”、“学习”和“学习”)“高级培训”),默认值为“教育”,该值可以为空

我编写了一个带有getter/setter的类包,比如
set_usage($usage)/get_usage()
,以及一个用于使用pdo访问数据库的类包:

class Packet_dao {
    private m_insert_query;
    ...
    public function persist($data)
    {
        $query = $this->m_insert_query;
        try
        {
           $stmt = $this->bind_param($data, $query);
           $stmt->execute();
           return true;
        }
        catch (PDOException $ex)
        {
           $this->m_error_message = $ex->getMessage();
           return false;
        }
    }

    private function bind_param($packet, $query)
    {
       $stmt = $this->m_pdo->prepare($query);
       $stmt->bindParam(':userId', $packet->get_user_id());
       ...
       $stmt->bindParam(':usage', $packet->get_usage());
       return $stmt;
    }
插入查询看起来像

INSERT INTO packets (userId, number, ..., `usage`) 
VALUES (:userId, Coalesce(:number, default(number)), Coalesce(:usage, default(`usage`)))
因此,如果我想在db中添加一个数据包,代码如下所示:

$packet = new Packet();
$packet_dao = new Packet_dao();
$packet->set_stuff("stuff");
$packet_dao->persist($packet);
到目前为止,一切正常


现在,应该添加另一个用例“fullversion”,而不是向枚举添加新值,他们决定使用NULL作为完整版本数据包的使用值。现在我遇到了一个问题:当我尝试使用
$packet->set_usage(NULL)设置使用值时
,它将被解释为与未设置值和默认值(“教育”)相同。我该怎么办?

显然,Coalesce()的第二个参数在我更改
Coalesce(:usage,default(usage))后,强制它在未设置任何内容(或NULL)时采用默认值
进入
:用法
。它起作用了

显然,在我更改
合并(:用法,默认(用法))后,Coalesce()的第二个参数强制它在未设置任何内容(或空值)时采用默认值
into
:用法
。如果一个值是
null
,那么
bindValue
bindParam
的第三个参数应该是
\PDO::PARAM\u null
。这意味着您必须在将其添加到
bindParam
插入数据包之前检查该值(userId,number,,“用法”)
如果这是你在
用法
列中引用的实际代码,那么你需要使用ticks
`
。这两种动物是完全不同的,会引发语法错误。如果你使用ticks,那么你应该修改你的问题,以避免让那些认为这就是问题所在,可能只想就这一点发表一个答案。@fred:是的,我知道,我只是不知道如何逃避`在这里,用引号编辑它:
$packet->set\u用法(“NULL”)
我认为应该可以。因为现在,您正试图输入NULL常量,而不是字符串,结果就是一个空值/空。@N.B.抱歉,但我想我需要更多帮助:-/。现在有两种情况:1.这是一个教育版本,所以我不会使用$packet->set\u usage()并让它接受默认值($packet->get_usage()将返回NULL)2.这是一个完整版本,我需要将usage的值设置为NULL。在这两种情况下,要绑定的值都是NULL,我如何告诉insert查询产生差异?如果值是
NULL
,那么
bindValue
bindParam
的第三个参数应该是
\PDO::PARAM\u NULL
。这意味着您必须进行检查将其添加到
bindParam
插入数据包之前的值(userId、number、,“用法”)
如果这是你在
用法
列中引用的实际代码,那么你需要使用ticks
`
。这两种动物是完全不同的,会引发语法错误。如果你使用ticks,那么你应该修改你的问题,以避免让那些认为这就是问题所在,可能只想就这一点发表一个答案。@fred:是的,我知道,我只是不知道如何逃避`在这里,用引号编辑它:
$packet->set\u用法(“NULL”)
我认为应该可以。因为现在,您正试图输入NULL常量,而不是字符串,结果就是一个空值/空。@N.B.抱歉,但我想我需要更多帮助:-/。现在有两种情况:1.这是一个教育版本,所以我不会使用$packet->set\u usage()并让它接受默认值($packet->get_usage()将返回NULL)2.这是一个完整版本,我需要将usage的值设置为NULL。在这两种情况下,要绑定的值都是NULL,我如何告诉insert查询产生差异?