《北京邮电大学计算机学与技术大三数据库第7次实验报告.doc》由会员分享,可在线阅读,更多相关《北京邮电大学计算机学与技术大三数据库第7次实验报告.doc(10页珍藏版)》请在三一办公上搜索。
1、北京邮电大学实验报告课程名称 数据库系统概念 实验名称 数据库接口实验 计算机系302班姓名 魏乐业 计算机系302班姓名 华逸群 教师_叶文,吴起凡_ 成绩_2013_年_6_月_3_日实验目的:1 通过编写数据库应用程序,培养数据库应用程序开发能力。 2 熟悉数据库应用程序设计的多种接口的配置,培养相关的软件配置能力。实验内容:1 了解通用数据库应用编程接口(例如JDBC、ODBC等)的配置方法。2 利用C语言(或其它支持某种数据库应用程序接口的高级程序设计语言)编程实现简单的数据库应用程序,掌握基于该接口的数据库访问的基本原理和方法。3 掌握静态嵌入式SQL语言程序设计的原理和方法。4
2、在数据库应用程序中,执行查找、增加、删除、更新等操作。5 选择适当的数据访问接口,比较高的要求为完成静态和动态嵌入式SQL的程序设计(需要两个程序),基本要求为两者选择其一。实验环境:1 采用SQL SERVER 2005数据库管理系统作为实验平台2 使用 microsoft Visual Studio 2010 作为应用程序编写的平台实验步骤及结果分析:1 在Windows控制面板中通过管理工具下的ODBC数据源工具在客户端新建连接到SQL SERVER数据库服务器的ODBC数据源,测试连接通过后保存。1) 打开控制面板的管理工具界面,进入ODBC数据源管理器对话框2) 选择系统DSN添加驱
3、动程序2、应用程序使用ODBC接口的详细步骤(1) 分配环境句柄:ODBC初始化,为ODBC分配环境句柄。调用函数SQLAllocHandle。设置环境属性:完成环境分配后,用函数SQLSetEnvAttr设置环境属性。释放环境句柄:完成数据访问任务时,应调用SQLFreeHandle释放前面分配的环境。(2) 分配连接句柄:声明一个SQLHDBC类型的变量,调用SQLAllocHandle函数分配句柄。设置连接属性:所有连接属性都可通过函数SQLSetConnectAttr设置,调用函数SQLGetConnectAttr可获取这些连接属性的当前设置值。(3) 连接数据源:对于不同的程序和用户
4、接口,可以用不同的函数建立连接。SQLConnect:该函数只要提供数据源名称、用户ID和口令,就可以进行连接了。SQLDriverConnect:该函数用一个连接字符串建立至数据源的连接,它可以让用户输入必要的连接信息,使用系统中还没定义的数据源。SQLBrowseConnect:该函数支持以一种迭代的方式获取到数据源的连接,直到最后建立连接,它基于客户机服务器体系结构,因此本地数据库不支持该函数。(4) 准备并执行SQL语句a 分配语句句柄:语句句柄是通过调用SQLAllocHandle函数分配的。函数SQLGetStmrrAttr和SQLSetStmrrAttr用来获取和设置一个语句句柄
5、的选项,使用完,调用SQLFreeHandle释放该句柄。b 执行SQL语句SQLExecDirect:该函数直接执行SQL语句,对于只执行一次的SQL语句来说,该函数是执行最快的方法。SQLPrepare和SQLExecute:对于需要多次执行的SQL语句来说,可先调用SQLPrepare准备SQL语句的执行,用SQLExecute执行准备好的语句。c 使用参数:使用参数可以使一条SQL语句多次执行,得到不同的结果。函数SQLBindParameter负责为参数定义变量,实现参数值的传递。(5) 获取记录集a 绑定列:首先必须分配与记录集中字段相对应的变量,然后通过函数SQLBindCol将
6、记录字段同程序变量绑定在一起,对于长记录字段,可以通过调用函数SQLGetData直接取回数据。绑定字段可以根据自己的需要全部绑定,也可以绑定其中的某几个字段。通过调用函数SQLBindCol将变量地址值赋为NULL,可以结束对一个记录字段的绑定,通过调用函数SQLFreeStmt,将其中选项设为SQL_UNBIND,或者直接释放句柄,都会结束所有记录字段的绑定。b SQLFetch:该函数用于将记录集的下一行变成当前行,并把所有捆绑过的数据字段的数据拷贝到相应的缓冲区。c 光标:应用程序获取数据是通过光标(Cursor)来实现的,在ODBC中,主要有3种类型的光标:单向光标、可滚动光标和块光
7、标。有些应用程序不支持可滚动光标和块光标,ODBC SDK提供了一个光标库(ODBCCR32.DLL),在应用程序中可通过设置连接属性(SQL_STTR_ODBC_CURSOR)激活光标库。(6) 记录的添加、删除和更新:数据源数据更新可通过3种方式:通过SQLExecDirect函数使用相应的SQL语句;调用SQLSetPos函数实现记录集定义更新;调用SQLBulkOperations函数实现数据更新。第一种方式适用于任何ODBC数据源,后两种方式有的数据源不支持,可调用SQLGetInfo确定数据源。SQLBulkOperations:该函数操作基于当前行集,调用前,须先调用SQLFet
8、ch或SQLFetchScroll获取。函数调用后,块光标的位置变为未定义状况,因此,应该先调用函数SQLFetchScroll设定光标位置。(7) 错误处理:每个ODBC API函数都能产生一系列反映操作信息的诊断记录,可以用SQLGetDiagField函数获取诊断记录中特定的域,另外,可以使用SQLGetDiagRec获取诊断记录中一些常用的域。(8) 事务处理:事务提交有两种方式:自动提交模式和手动提交模式。应用程序可通过调用函数SQLSetConnectAttr设定连接属性SQL_ATTR_AUTOCOMMIT,自动提交模式是默认的连接属性设置,对于所有的ODBC驱动程序都能适应这种
9、模式下,所有语句都是作为一个独立的事务进行处理的。手动提交模式把一组SQL语句放入一个事务中,程序必须调用函数SQLEenTran明确地终止一个事务。若使用多个激活的事务,就必须建立多个连接,每一个连接包含一个事务。(9) 断开数据连接并释放环境句柄:完成数据库操作后,可调用SQLDisconnect函数关闭同数据库的连接。3、 以实验二建立的数据库为基础,编写 C语言(或其它支持ODBC/JDBC等接口的高级程序设计语言) 数据库应用程序,利用SQLExecDirect语句,实现数据库应用程序对数据库中表(有数据)进行数据查询、删除、插入、更新等操作。要求先打印出所有记录,然后删除一行,再打
10、印一次,进行更新,再打印一次,最后插入,再打印一次1) 代码编写见附件2) 实验运行结果a select * from MS 语句执行直接结果在命令行打印b BSC表中原始数据执行语句update BSC set MscID = 9011 where BscId = 42215 BSC表中数据改变c Antenna 表中原始数据执行语句insert into Antenna values(1,1,1,1,1,1,1,1) Antenna表中数据改变实验总结:配置OBDC数据源时,我们参考了网上的配置步骤,在服务器名称时出现了点问题,不过总的实现还算是比较容易的。代码编写主要参考附件中的ODBC
11、接口函数,在执行的时候发现一些问题,开始的时候仅有select 语句可以执行,而update 和 insert 语句执行的返回集均是-1,我们一直在代码中寻找问题,但是找了很久也没有发现问题。最后我们将要执行的语句放入SQL sever 中执行后,也发现错误,其实不是代码的问题,而是我们所使用的那个表存在外键关联,而插入的外键值是关联表中所没有的取值。数据库与应用程序连接,可以扩展程序的功能和使用范围,同时也增加了数据库的使用范围。但这次实验的错误告诉我们应用程序连接到数据库时也要考虑数据库本身所有的一些限制条件。附件1/*程序源代码:*/#include #include #include
12、#include sql.h#include sqltypes.h#include sqlext.hRETCODE retcode;/结果返回集HDBC hdbc;/定义链接句柄HENV henv; /定义环境句柄HSTMT hstmt;/定义语句句柄HSTMT hstmt1;/定义语句句柄void SQL(unsigned char);/执行SQL语句子程序int main() unsigned char SY=GSM;/ODBC数据源名称 unsigned char sqll=sa;/用户名 unsigned char pwd=123;/密码 /分配ODBC环境retcode=SQLAll
13、ocEnv(&henv); /分配环境retcode=SQLAllocConnect(henv, &hdbc);/获取连接句柄retcode=SQLConnect(hdbc,(SQLCHAR *)GSM,SQL_NTS,(SQLCHAR *)sa,SQL_NTS,(SQLCHAR *)123,SQL_NTS);/数据库连接unsigned char yuju=select * from MSC; /sql语句char MscID80;char MscName80;char MscCompany80; long lenOut1,lenOut2,lenOut3;retcode=SQLAllocSt
14、mt(hdbc,&hstmt);/分配语句retcode=SQLExecDirect(hstmt,yuju,SQL_NTS);/执行sql语句if(retcode = SQL_SUCCESS)/将结果集中的属性列一一绑定至变量SQLBindCol(hstmt,1,SQL_C_CHAR,MscID,sizeof(MscID),&lenOut1);SQLBindCol(hstmt,2,SQL_C_CHAR,MscName,sizeof(MscName),&lenOut2);SQLBindCol(hstmt,3,SQL_C_CHAR,MscCompany,sizeof(MscCompany),&le
15、nOut3); /把所有捆绑过的数据字段的数据拷贝到相应的缓冲区 printf(%sn,yuju);printf(MscID MscName MscCompany n);retcode=SQLFetch(hstmt);/printf(%d,retcode);while(retcode = SQL_SUCCESS | retcode = SQL_SUCCESS_WITH_INFO)printf(%s %s %sn,MscID,MscName,MscCompany); /把所有捆绑过的数据字段的数据拷贝到相应的缓冲区retcode=SQLFetch(hstmt); SQLFreeStmt(hstm
16、t,SQL_DROP);/释放语义句柄/unsigned char del=select * from MSC;/SQL(del); unsigned char update=update BSC set MscID = 9011 where BscId = 42214;SQL(update);unsigned char insert=insert into Antenna values(1,1,1,1,1,1,1,1);SQL(insert);SQLDisconnect(hdbc); SQLFreeConnect(hdbc); /释放链接句柄SQLFreeEnv(henv); / 释放ODBC 环境句柄system(pause);return 0;void SQL(unsigned char aaa) HSTMT hstmt;/定义语句句柄retcode=SQLAllocHandle(SQL_HANDLE_STMT, hdbc, &hstmt); /分配语义句柄if(retcode=SQL_SUCCESS)retcode=SQLExecDirect(hstmt,aaa,SQL_NTS);printf(%d,retcode); SQLFreeStmt(hstmt,SQL_DROP); /释放语句句柄