准备好的执行

ODBC API 将准备的执行定义为减少与重复执行 Transact-SQL 语句关联的分析和编译开销的方法。 应用程序生成一个包含 SQL 语句的字符串,然后在两个阶段执行它。 它调用 SQLPrepare 函数 一次,使语句由数据库引擎分析并编译为执行计划。 然后,它会针对已准备的执行计划的每个执行调用 SQLExecute 。 这会保存每次执行时分析和编译开销。 准备的执行通常由应用程序用来重复执行相同的参数化 SQL 语句。

对于大多数数据库,准备的执行速度比直接执行的语句执行速度要快三到四倍以上,主要是因为语句只编译一次,而每次执行语句时直接执行的语句都会进行编译。 准备好的执行还可以减少网络流量,因为每次执行语句时,驱动程序都可以将执行计划标识符和参数值(而不是整个 SQL 语句)发送到数据源。

SQL Server 通过改进的算法从 SQLExecDirect 检测和重用执行计划,减少了直接执行与准备的执行之间的性能差异。 这使得准备好的执行的一些性能优势可供直接执行的语句使用。 有关详细信息,请参阅 直接执行

SQL Server 还为准备的执行提供本机支持。 执行计划基于 SQLPrepare 生成,并在调用 SQLExecute 时执行。 由于 SQL Server 不需要在 SQLPrepare 上生成临时存储过程, 因此 tempdb 中的系统表没有额外的开销。

出于性能原因,语句准备推迟到调用 SQLExecute 或执行元属性作(例如 ODBC 中的 SQLDescribeColSQLDescribeParam )。 这是默认行为。 在执行语句或执行元属性作之前,准备的语句中的任何错误都未知。 将 SQL Server Native Client ODBC 驱动程序特定的语句属性SQL_SOPT_SS_DEFER_PREPARE设置为SQL_DP_OFF可以关闭此默认行为。

如果准备延迟,在调用 SQLExecute 之前调用 SQLDescribeCol 或 SQLDescribeParam 会生成到服务器的额外往返。SQLDescribeCol 上,驱动程序从查询中删除 WHERE 子句,并将其发送到具有 SET FMTONLY ON 的服务器,以获取查询返回的第一个结果集中列的说明。 在 SQLDescribeParam 上,驱动程序调用服务器以获取查询中任何参数标记引用的表达式或列的说明。 此方法还存在一些限制,例如无法在子查询中解析参数。

SQLPrepare 与 SQL Server Native Client ODBC 驱动程序过度使用会降低性能,尤其是在连接到早期版本的 SQL Server 时。 不应将准备的执行用于一次执行的语句。 对于单个语句执行,准备的执行速度比直接执行慢,因为它需要从客户端到服务器的额外网络往返。 在早期版本的 SQL Server 上,它还生成临时存储过程。

准备的语句不能用于在 SQL Server 上创建临时对象。

每当使用 SQLBindParameter 时,某些早期 ODBC 应用程序都使用了 SQLPrepareSQLBindParameter 不需要使用 SQLPrepare,它可与 SQLExecDirect 一起使用。 例如,将 SQLExecDirectSQLBindParameter 配合使用,从仅执行一次的存储过程检索返回代码或输出参数。 请勿将 SQLPrepareSQLBindParameter 一起使用,除非多次执行同一语句。

另请参阅

执行语句 (ODBC)