mysql准备:会话变量与参数&;局部变量

mysql准备:会话变量与参数&;局部变量,mysql,prepared-statement,Mysql,Prepared Statement,我正在使用存储过程并准备语句。我想发送参数来定义从select语句返回的列。如果我使用会话变量,而不替换变量,这是可行的。我可以解决这个问题,但我想了解这个问题。以下是一些例子: 这项工作: DELIMITER $$ DROP PROCEDURE IF EXISTS `pnlByTheme` $$ CREATE PROCEDURE `pnlByTheme`(IN param VARCHAR(50)) BEGIN set @sqlStmt = concat("select ",param,"

我正在使用存储过程并准备语句。我想发送参数来定义从select语句返回的列。如果我使用会话变量,而不替换变量,这是可行的。我可以解决这个问题,但我想了解这个问题。以下是一些例子:

这项工作:

DELIMITER $$
DROP PROCEDURE IF EXISTS `pnlByTheme` $$
CREATE PROCEDURE `pnlByTheme`(IN param VARCHAR(50))
BEGIN
  set @sqlStmt = concat("select ",param," from pnl_aggregate");
  prepare stmt from @sqlStmt;
  execute stmt;
deallocate prepare stmt;
END $$
DELIMITER ;
当我调用pnlByTheme('label')时,我会像从命令行一样从pnl_aggregate获得selectlabel的结果。如果我将set语句更改为:

set @sqlStmt = "select ? from pnl_aggregate";
execute stmt using param;
然后我将execute语句更改为:

set @sqlStmt = "select ? from pnl_aggregate";
execute stmt using param;
mysql不喜欢这样,也不会创建过程。如果我改为:

DELIMITER $$

DROP PROCEDURE IF EXISTS `pnlByTheme` $$
CREATE PROCEDURE `pnlByTheme`(IN param VARCHAR(50))
BEGIN
  set @p = param;
  set @sqlStmt = "select ? from pnl_aggregate";
  prepare stmt from @sqlStmt;
  execute stmt using @p;
deallocate prepare stmt;
END $$

DELIMITER ;
这将创建一个过程。为什么?奇怪的是(无论如何,对我来说)电话的结果

call pnlbytheme('label');

只是字面上的每一行的“标签”,而不是我正在寻找的实际数据。我可以使用concat轻松解决这个问题,但我想了解。请帮忙。

好的,谢谢那些看过的人。发布后,当相关问题出现时,我找到了答案。有时我们(或者至少我)并不总是知道如何寻找我们想要的东西。无论如何,这里有两个答案:

1) 准备好的发言是全球性的。请参阅和(查找“准备好的语句对会话也是全局的”)。虽然我不是100%清楚这一点,但结果是需要会话变量。答案是贾斯汀·格兰特

2) “参数标记只能在数据值应该出现的地方使用,不能用于SQL关键字、标识符等。”来自,Devart在这里回答了这个问题

我也觉得很有帮助。谢谢你,卡西诺。

我找到了部分答案(是的,我在发帖前确实看过)。看见这就解释了准备好的语句是会话全局的,这似乎转化为使用会话变量。但是我仍然不知道为什么@p的替代并没有达到预期的效果。