/* 包含C头文件 */
#include <stdio.h>
#include <stdlib.h>
#include <string.h> /* 包含SQLCA头文件 */
#include <sqlca.h> /* 定义绑定变量值和 选择列表项值的最大长度
* 绑定变量:即在SQL语句中输入的“&”占位符。
*/
#define MAX_VAR_LEN 30 /* 定义选择列表项名的最大长度 */
#define MAX_NAME_LEN 31 /* 定义宿主变量 */
exec sql begin declare section;
char *usrname = "scott";
char *passwd = "";
char *serverid = "orcl";
char sql_stat[];
char current_date[];
exec sql end declare section; void sql_error(void);
void connet(void);
void process_input(void);
void process_output(void); int main(void)
{
/* 安装错误处理句柄 */
exec sql whenever sqlerror do sql_error(); /* 连接到数据库 */
connet(); /*
* 分配输入描述区和输出描述区
* Ansi定义了该套标准,proc程序开发者按标准实现了它
* 这两条语句在proc编译的时候会开辟对应大小的存储空间
*/
exec sql allocate descriptor 'input_descriptor'; //用来存储输入的宿主变量
exec sql allocate descriptor 'output_descriptor'; //用来缓存数据库端返回的结果集 for( ; ; )
{
printf("\n请输入动态SQL语句(EXIT:退出):\n");
gets(sql_stat); /* EXIT(exit)->退出 */
if( == strncmp(sql_stat , "EXIT" , ) || == strncmp(sql_stat , "exit" , ))
break; /* 准备动态SQL语句 */
exec sql prepare s from :sql_stat; /* 定义游标 */
exec sql declare c cursor for s; /* 处理绑定变量 , 即处理占位符 “&” */
process_input(); /*
* 打开游标成功 意寓着结果已经被保存到输出描述区了。
* select语句:处理查询结果
* 其他SQL语句:执行
*/
exec sql open c using descriptor 'input_descriptor';
if( == strncmp(sql_stat , "SELECT" , ) , == strncmp(sql_stat , "select" , ))
{
process_output();
}
/* 关闭游标 */
exec sql close c;
} /* 释放输入描述区和输出描述区 */
exec sql deallocate descriptor 'input_descriptor';
exec sql deallocate descriptor 'output_descriptor'; /* 提交事务,断开连接 */
exec sql commit work release;
puts("谢谢使用ANSI动态SQL!\n"); return ;
} void sql_error(void)
{
/* 显示SQL错误号、错误描述 */
printf("%.*s\n" , sqlca.sqlerrm.sqlerrml , sqlca.sqlerrm.sqlerrmc);
exit();
} void process_input(void)
{
int i; /* 定义宿主变量 */
exec sql begin declare section;
int input_count;
int input_type ;
int input_len;
char input_buffer[MAX_VAR_LEN];
char name[MAX_NAME_LEN];
int occurs;
exec sql end declare section; /* 绑定变量->输入描述区 */
exec sql describe input s using descriptor 'input_descriptor'; /* 取得绑定变量个数 */
exec sql get descriptor 'input_descriptor' :input_count = count; /* 循环处理绑定变量名 */
for(i = ; i != input_count ; ++i)
{
occurs = i + ; /* 取得绑定变量名 */
exec sql get descriptor 'input_descriptor' value :occurs :name = name;
printf("请输入%s的值:" , name);
gets(input_buffer); /* 以NULL结尾 */
input_len = strlen(input_buffer);
input_buffer[input_len] = '\0'; /* 设置绑定变量类型、长度和值 */
input_type = ;
exec sql set descriptor 'input_descriptor' value :occurs
type = :input_type , length = :input_len , data = :input_buffer;
}
} void process_output(void)
{
int i; // 定义宿主变量
EXEC SQL BEGIN DECLARE SECTION ;
int output_count;
int output_type;
int output_len;
char output_buffer[MAX_VAR_LEN];
short output_indicator;
char name[MAX_NAME_LEN];
int occurs;
EXEC SQL END DECLARE SECTION ; // 选择列表项->输出描述区
exec sql describe output s using descriptor 'output_descriptor'; //取得选择列表项个数
exec sql get descriptor 'output_descriptor' :output_count = count; //循环处理选择列表项(即列名,或者叫表头) output_type = ; //设置类型为变长字符串varchar for(i = ; i != output_count ; ++i)
{
occurs = i + ; output_len = MAX_VAR_LEN; // 设置选择列表项的类型和长度(设置每一列,按照varchar类型进行显示)
exec sql set descriptor 'output_descriptor' value :occurs
type = :output_type , length = :output_len; //取得选择列表项的名称并输出
exec sql get descriptor 'output_descriptor' value :occurs :name = name; //显示选择列表项名称
printf("\t%s" , name);
}
printf("\n"); // 提取数据完毕->退出循环
exec sql whenever not found do break; // 循环处理选择列表项数据
for( ; ; )
{
// 行数据-> fetch into 利用游标从输出描述区读取数据。
exec sql fetch c into descriptor 'output_descriptor'; // 循环处理每列数据
for(i = ; i < output_count ; ++i)
{
occurs = i + ; // 取得列数据和指示变量值
exec sql get descriptor 'output_descriptor' VALUE :occurs
:output_buffer = DATA , :output_indicator = INDICATOR; //输出列数据
if(- == output_indicator)
printf("\t%s", " ");
else
printf("\t%s" , output_buffer);
}
printf("\n");
}
} void connet(void)
{
int ret = ;
//连接数据库
EXEC SQL CONNECT:usrname IDENTIFIED BY:passwd USING:serverid ;
if (sqlca.sqlcode != )
{
ret = sqlca.sqlcode;
printf("sqlca.sqlcode: err:%d \n", sqlca.sqlcode);
return ;
} else {
printf("connect ok...\n");
}
}

1.ASNI 与 ORACLE 实现动态sql的最大区别就在于不用关心描述区的动态扩容,因为ASNI已经封装好了接口,直接调用就成。

2.也是主要分为两部分:输出描述区和输入描述区。两个区的作用同ORACLE 功能一样。

* 分配输入描述区和输出描述区
* Ansi 定义了该套标准,proc 程序开发者按标准实现了它
* 这两条语句在 proc 编译的时候会开辟对应大小的存储空间
*/
exec sql allocate descriptor 'input_descriptor'; //用来存储输入的宿主变量
exec sql allocate descriptor 'output_descriptor'; //用来缓存数据库端返回的结果集

ANSI实现动态 sql的更多相关文章

  1. 值得注意的ibatis动态sql语法格式

    一.Ibatis常用动态sql语法,简单粗暴用一例子 <select id="iBatisSelectList" parameterClass="java.util ...

  2. Mysql - 游标/动态sql/事务

    游标这个在我目前的项目里面用的还不多, 但是其功能还是很强大的. 动态sql以前都没用过, 是跟着富士康(不是张全蛋的富土康哦)过来的同事学的. 还是挺好用的. 我的数据库方面, 跟他学了不少. 在此 ...

  3. MyBatis4:动态SQL

    什么是动态SQL MyBatis的一个强大特性之一通常是它的动态SQL能力.如果你有使用JDBC或其他相似框架的经验,你就明白条件串联SQL字符串在一起是多么地痛苦,确保不能忘了空格或者在列表的最后的 ...

  4. 分享公司DAO层动态SQL的一些封装

    主题 公司在DAO层使用的框架是Spring Data JPA,这个框架很好用,基本不需要自己写SQL或者HQL就能完成大部分事情,但是偶尔有一些复杂的查询还是需要自己手写原生的Native SQL或 ...

  5. MySQL存储过程动态SQL语句的生成

    用Mysql存储过程来完成动态SQL语句,使用存储过程有很好的执行效率: 现在有要求如下:根据输入的年份.国家.节假日类型查询一个节假日,我们可以使用一般的SQL语句嵌入到Java代码中,但是执行效率 ...

  6. 【Java EE 学习 79 下】【动态SQL】【mybatis和spring的整合】

    一.动态SQL 什么是动态SQL,就是在不同的条件下,sql语句不相同的意思,曾经在“酒店会员管理系统”中写过大量的多条件查询,那是在SSH的环境中,所以只能在代码中进行判断,以下是其中一个多条件查询 ...

  7. 自定义函数执行动态sql语句

    --函数中不能调用动态SQL,使用用存储过程吧.如果还要对函数做其他操作,换成存储过程不方便,可以考虑把其他操作一起封装在存储过程里面.如:   create proc [dbo].[FUN_YSCL ...

  8. mybatis入门基础(五)----动态SQL

    一:动态SQL 1.1.定义 mybatis核心对sql语句进行灵活操作,通过表达式进行判断,对sql进行灵活拼接.组装. 1.2.案例需求 用户信息综合查询列表这个statement的定义使用动态s ...

  9. mybatis 动态sql表达式相关应用

    一.mybatis 表达式简介 对于mybatis3 ,提供了一种动态sql的方式.通过动态sql我们可以直接在mybatis 的xm映射文件中直接通过条件判断的方式进行查询添加的拼接.mybatis ...

随机推荐

  1. (转)Linux下数据段的区别(数据段、代码段、堆栈段、BSS段)

    进程(执行的程序)会占用一定数量的内存,它或是用来存放从磁盘载入的程序代码,或是存放取自用户输入的数据等等.不过进程对这些内存的管理方式因内存用途 不一而不尽相同,有些内存是事先静态分配和统一回收的, ...

  2. linux禁ping与限制ip登录

    以root进入linux系统,然后编辑文件icmp_echo_ignore_allvi /proc/sys/net/ipv4/icmp_echo_ignore_all将其值改为1后为禁止PING将其值 ...

  3. opensue fstab故障恢复

    date: 20140505 author: Jin 故障背景: 早上启动本本 无法启动,报错信息(几个关键) WARNING:Failed to connect to lvmetad: No suc ...

  4. CentOS 6.9下双网卡绑定单个IP地址及装网卡绑定到一个网桥(转)

    说明:经过查阅,原来双网卡绑定一个IP的专业名词叫做bond,可以实现负载均衡:如果想要实现两张网卡绑定到一个网桥,基本思路是两张网卡设置同一个网桥是行不通的,但如果先实现bond,然后将bond绑定 ...

  5. 实现自动解析properties文件并装配到Bean

    主要实现了,配置的属性就装配, 没有配置的属性不装配 思路: 1 . 通过反射获取类内部所有方法名称 2 . 获取perperties 的key集合 3 .  处理字符串,比较两个匹配,如果匹配成功就 ...

  6. Android内存优化11 内存泄漏常见情况2 内部类泄漏

    线程持久化 Java中的Thread有一个特点就是她们都是直接被GC Root所引用,也就是说Dalvik虚拟机对所有被激活状态的线程都是持有强引用,导致GC永远都无法回收掉这些线程对象,除非线程被手 ...

  7. 常见Linux命令(非文件操作)

    可见 http://man.linuxde.net/systemctl 非常详尽

  8. raymarching

    http://www.michaelwalczyk.com/blog/2017/5/25/ray-marching https://kosmonautblog.wordpress.com/2017/0 ...

  9. php 基于cookie的sessIon机制

    session_start()是session机制的开始,它有一定概率开启垃圾回收,因为session是存放在文件中,PHP自身的垃圾回收是无效的,SESSION的回收是要删文件的,这个概率是根据ph ...

  10. 记一次vue2项目部署nginx静态文件404解决过程

    github上下的一个vue2的项目,运行可以的,webpack打包后,nginx请求报错: 发现路径很奇怪啊,所以果断来到build.js文件中看看是不是哪里不对. 已经一番引用查找: 发现在这里配 ...