一些应用程序必须在运行时接受(或构建)并处理各种SQL语句 这种在程序执行临时生成的 SQL 语句叫动态 SQL 语句. 利用动态 SQL 来编写 Pro*C 程序的方法叫动态 SQL 技术.。也就是说SQL语句的组成直到运行时才知道。这样的语句可以(而且可能会)在执行过程中发生变化。 当出现下列情况, 就需要使用动态 SQL 技术: 1. SQL 语句的文本未知. 2. 宿主变量的个数未知。 3. 宿主变量的数据类型未知。 4. 引用的数据库对象未知, 如列, 索引, 序列, 表, 用户名和视图.
只能执行非查询语句(非select), 且在非查询动态 SQL 语句内不能包含输入宿主变量占位符
demo1 //> update dept set loc= ‘bj’ where deptno=89 //>insert into dept values(88, ‘CJ’, ‘TJ’) #include <stdio.h> #include <string.h> #include <stdlib.h> #include "sqlca.h" #include "oraca.h" //定义宿主变量 EXEC SQL BEGIN DECLARE SECTION; char *serverid = "c##scott/root"; char Sqlstatements[1024]; char *pSql; EXEC SQL END DECLARE SECTION; extern sqlgls(char * , size_t *, size_t * ); extern sqlglmt(void *,char *,size_t *,size_t *); int connet(); void doerr(); //非select语言,无宿主变量 int main() { int ret = 0; char inputchar; memset(Sqlstatements, 0, sizeof(Sqlstatements)); pSql = NULL; EXEC SQL WHENEVER SQLERROR DO doerr(); connet(); pSql = mySql; //循环处理sql语言 for(;;) { printf("\nplease enter sql(not select ): "); gets(mySql); //scanf("%s", mySql); --空格截断 printf("mysql>%s\n", mySql); printf("任意键继续执行....\n"); getchar(); EXEC SQL EXECUTE IMMEDIATE :pSql; EXEC SQL COMMIT; printf("continue?\n"); scanf("%c", &inputchar); fflush(stdin); if (inputchar=='n' || inputchar=='N') { break; } } EXEC SQL COMMIT WORK RELEASE; return ret ; } int connet() { int ret = 0; //连接数据库 EXEC SQL connect :serverid; if (sqlca.sqlcode != 0) { ret = sqlca.sqlcode; return ret; } else { printf("connect ok...\n"); } return ret; } void doerr() { char szerrbuf[120]; size_t outputlen, inputlen = 120; unsigned int ret = 0; //出错时,可以把错误SQL语言给打印出来 EXEC SQL WHENEVER SQLERROR CONTINUE; ret = sqlgls(szerrbuf, &inputlen, &outputlen); printf("SQL:%.*s\n", inputlen, szerrbuf); printf("提示:%.*s\n", sqlca.sqlerrm.sqlerrml, sqlca.sqlerrm.sqlerrmc); EXEC SQL ROLLBACK WORK RELEASE; exit(1); }