【问题标题】:MySQL PDO - how to deal with question marks in field namesMySQL PDO - 如何处理字段名称中的问号
【发布时间】:2020-04-09 03:27:05
【问题描述】:

我继承了一个 MySQL 数据库,其字段名称如下:

'Profile is Subscribed ?' & 'Private ?'

这些无法更改,因为该表由企业内的不同系统使用。

但是,我想使用 PHP PDO 来更新这些记录。

例如:UPDATE Guests SET `Profile is Subscribed ?` = :subscribed, `Private ?` = :private WHERE intID = 123;

但是,当使用占位符时,我收到“混合名称和位置参数”错误消息。

是否有解决方法(不涉及重命名字段)?我可以避开问号吗(我试过“/?”,但没有区别)?

谢谢

【问题讨论】:

  • 使用反引号圆形列和表名
  • EGUPDATE Guests SET `Profile is Subscribed ?` = :subscribed, `Private ?` = :private WHERE intID = 123
  • 列名已经在使用反引号。
  • 您现在已经更新了问题中的代码。这是否意味着这不是您实际代码的复制/粘贴,而是在这里为我们重写?请不要那样做。始终发布实际代码。如果您想发布您尝试过的内容,请将其添加到问题中,但保留原始内容。
  • “您真的需要查看名称中没有问号的 100 多个字段吗?” - 一个最小的工作示例会有所帮助。还要检查您的数据库的排序规则。

标签: php mysql pdo


【解决方案1】:

这似乎是 PDO 中的一个错误。如果我尝试

$stmt = $pdo->prepare('
    UPDATE Guests SET
      `Profile is Subscribed ?` = :subscribed,
      `Private ?` = :private
    WHERE intID = 123
');
$stmt->execute(['subscribed' => 1, 'private' => 0]);

我收到此错误:

PDOException: SQLSTATE[HY093]: 参数号无效:混合命名 和...中的位置参数

解决方法:不要使用命名占位符。请改用?。但是你需要以正确的顺序绑定值:

$pdo->setAttribute(PDO::ATTR_EMULATE_PREPARES, false);

$stmt = $pdo->prepare('
    UPDATE Guests SET 
      `Profile is Subscribed ?` = ?,
       `Private ?` = ?
     WHERE intID = 123
');
$stmt->execute([1,0]);

将ATTR_EMULATE_PREPARES 设置为false 很重要。否则你会得到另一个错误:

PDOException: SQLSTATE[HY093]: Invalid parameter number: number of 绑定变量与...中的标记数不匹配

另一种解决方法是使用SQL模式ANSI_QUOTES:

$pdo->exec("SET SESSION sql_mode = concat(@@sql_mode, ',ANSI_QUOTES')");
$stmt = $pdo->prepare('
    UPDATE Guests SET
      "Profile is Subscribed ?" = :subscribed,
      "Private ?" = :private 
    WHERE intID = 123
');
$stmt->execute(['subscribed' => 1, 'private' => 0]);

但就个人而言 - 我宁愿重命名列名。

【讨论】:

  • 同意重命名列。在列名中使用标点符号是不必要的风险。您不会在任何编程语言的变量名中这样做。
  • 谢谢 Paul - SQL 模式 ANSI_QUOTES 是我在这种情况下需要的修复程序。我同意,我永远不会有这样的列名,但在这种情况下,我无法更改它们!再次感谢您。
  • @BillKarwin - 我在 PHP 中看到过类似 ${'Profile is Subscribed ?'} = ...; 的东西 :-)
  • 这也完全没有必要! :)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2021-10-16
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-09-14
  • 1970-01-01
  • 2012-10-04
相关资源
最近更新 更多