SQL Server:在 EXEC 中执行动态/内联 sql 表名称并将几何图形作为几何参数传递
我正在尝试在存储过程中执行内联 SQL 语句。我正在使用 SQL Server 2008。
问题是我无法执行第一个内联语句(带有 WHERE
子句)。它崩溃是因为 EXEC(...)
中的字符串是动态创建的,并且所有连接的变量必须是 varchar
类型。
调用过程时出现错误:
在上下文中指定的非布尔类型表达式,其中 预计情况会接近“订单”。
该过程如下所示:
CREATE PROCEDURE loadMyRows
@table_name nvarchar(50),
@bounding_box varchar(8000)
AS
BEGIN
-- *********************************** COMMENT *********************************
-- ** This two code lines are correct and will return true (1) or false (0), **
-- ** but they doesn't work within inline EXEC(...) **
--DECLARE @bb geometry = geometry::STGeomFromText(@bounding_box, 4326);
--select TOP(5) wkt.STWithin(@bb) AS 'bool'
-- *********************************** COMMENT *********************************
IF @bounding_box <> ''
BEGIN
DECLARE @bb geometry = geometry::STGeomFromText(@bounding_box, 4326);
EXEC(
'SELECT TOP (' + @row_limit + ') * ' +
'FROM ' + @real_table_name + ' ' +
'WHERE wkt.STWithin('+@bb+') ' + -- <-- doesn't work :-(
-- 'WHERE wkt.STWithin(geometry::STGeomFromText('''+@bounding_box+''', 4326)) ' +
-- ^^ doesn't work, too :-(
'ORDER BY id ASC '
);
END
ELSE
BEGIN
EXEC(
'SELECT TOP (' + @row_limit + ') * ' +
'FROM ' + @real_table_name + ' ' +
'ORDER BY id ASC'
);
END
END
I'm trying to execute an inline SQL statement within a stored procedure. I'm working with SQL Server 2008.
The problem is that I can't execute the first inline statement (with WHERE
clause). It crashes because the string within EXEC(...)
is dynamically created and all concatenated variables must be of type varchar
.
Error that appears when calling procedure:
An expression of non-boolean type specified in a context where a
condition is expected, near 'ORDER'.
The procedure looks like:
CREATE PROCEDURE loadMyRows
@table_name nvarchar(50),
@bounding_box varchar(8000)
AS
BEGIN
-- *********************************** COMMENT *********************************
-- ** This two code lines are correct and will return true (1) or false (0), **
-- ** but they doesn't work within inline EXEC(...) **
--DECLARE @bb geometry = geometry::STGeomFromText(@bounding_box, 4326);
--select TOP(5) wkt.STWithin(@bb) AS 'bool'
-- *********************************** COMMENT *********************************
IF @bounding_box <> ''
BEGIN
DECLARE @bb geometry = geometry::STGeomFromText(@bounding_box, 4326);
EXEC(
'SELECT TOP (' + @row_limit + ') * ' +
'FROM ' + @real_table_name + ' ' +
'WHERE wkt.STWithin('+@bb+') ' + -- <-- doesn't work :-(
-- 'WHERE wkt.STWithin(geometry::STGeomFromText('''+@bounding_box+''', 4326)) ' +
-- ^^ doesn't work, too :-(
'ORDER BY id ASC '
);
END
ELSE
BEGIN
EXEC(
'SELECT TOP (' + @row_limit + ') * ' +
'FROM ' + @real_table_name + ' ' +
'ORDER BY id ASC'
);
END
END
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
我已经找到了解决这个问题的有效方法。 MSDN 向我展示的方式是 http://msdn.microsoft.com/en- US/library/ms175170.aspx。里面写着:
这让我知道,如果我想使用表变量作为字符串执行动态语句,这与我在没有
EXECUTE
命令的情况下执行查询相同,例如:这可能不适用于表名。
所以,如果我改为:
那么,这就会起作用。这是因为我将 @sql_statement 简单地定义为一个串联字符串,它将在运行时将动态表名称解析为具有实际现有表名称的字符串。 @limit 参数未受影响,仍然是一个参数。
如果我们随后执行该批处理,我们只需传递 @limit 参数的值,它就可以工作了!
对于几何参数,它以相同的方式工作:
希望这很清楚;-)
I've found a working solution for this problem. The way the MSDN showed me was http://msdn.microsoft.com/en-US/library/ms175170.aspx. There's written:
That let me know, if I want to execute a dynamic statement with a table variable as string, it's the same as I would execute the query without the
EXECUTE
command, like:And this would probably not work for the table name.
So, if I write instead:
Then, this would work. This is because I define the @sql_statement simply as a concatenated string which will just resolve the dynamic table name at runtime to a string with the name of the real existing table. The @limit parameter is untouched and is still a parameter.
If we then execute the batch we only must pass a value for the @limit parameter and it works!
For the geometry parameter it works in the same way:
Hope this was clear ;-)