Mysql数据库的api介绍讲解

<div class="iteye-blog-content-contain" style="font-size: 14px"><p>&lt;div id="Article"&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;链接的流程图&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;&lt;img alt="这里写图片描述" src="/uploadfile/Collfiles/20171118/2017111809063750.png" /&gt;&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;h3&gt;一,API介绍&lt;/h3&gt;&nbsp;</p>
<p>&nbsp;&lt;h4&gt;1,初始化函数&lt;/h4&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;MYSQL *&lt;a href="https://www.2cto.com/database/MySQL/" target="_blank" class="keylink"&gt;mysql&lt;/a&gt;_init(MYSQL *mysql)&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;mysql 可以传 NULL&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;返回 分配的句柄 MYSQL*指针&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;h4 id="2连接到mysql&amp;lt;a href=" https:="" www.2cto.com="" atabase="" target="_blank" class="keylink"&gt;数据库&amp;quot;&amp;gt;2,连接到my&lt;a href="https://www.2cto.com/database/" target="_blank" class="keylink"&gt;sql数据库&lt;/a&gt;&lt;/h4&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;MYSQL *mysql_real_connect(MYSQL *mysql, const char *host, const char *user, const char *passwd, const char *db, unsigned int port, const char *unix_socket, unsigned long client_flag)&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;参数介绍&lt;/p&gt; mysql 初始化的句柄指针 host 主机地址 user 用户名 &ndash; mysql数据库 root passwd 用户的密码 db 要连接的数据库 port 端口 一般填0,mysql默认端口 3306 unix_socket 本地套接字 ,一般填NULL client_flag 连接标志 一般填0&nbsp;</p>
<p>&nbsp;&lt;p&gt;&lt;strong&gt;返回值:&lt;/strong&gt; 成功返回 连接句柄,失败返回 NULL&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;h4 id="3设定登陆的字符集-登陆之后"&gt;3,设定登陆的字符集 &ndash; 登陆之后&lt;/h4&gt;&nbsp;</p>
<p>&nbsp;&lt;blockquote&gt;&nbsp;</p>
<p>&nbsp; &lt;p&gt;int mysql_set_character_set(MYSQL *mysql, char *csname)&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;/blockquote&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;参数:&lt;/p&gt; mysql 连接句柄 csname 字符集的名称 utf8&nbsp;</p>
<p>&nbsp;&lt;h4 id="4query功能非常强大-增删改查都可以"&gt;4,query功能非常强大 增删改查都可以&lt;/h4&gt;&nbsp;</p>
<p>&nbsp;&lt;blockquote&gt;&nbsp;</p>
<p>&nbsp; &lt;p&gt;int mysql_query(MYSQL *mysql, const char *query)&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;/blockquote&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;参数介绍:&lt;/p&gt; mysql 连接句柄 query 执行的sql&nbsp;</p>
<p>&nbsp;&lt;p&gt;返回值:&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;pre class="brush:sql;"&gt;</p>
<p>成功 返回 0</p>
<p>失败 返回 非0</p>
<p>&lt;/pre&gt;&nbsp;</p>
<p>&nbsp;&lt;h4 id="5获得结果集的函数"&gt;5,获得结果集的函数&lt;/h4&gt;&nbsp;</p>
<p>&nbsp;&lt;blockquote&gt;&nbsp;</p>
<p>&nbsp; &lt;p&gt;MYSQL_RES *mysql_store_result(MYSQL *mysql)&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;/blockquote&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;返回值: 如果读取结果集失败,mysql_store_result()还会返回Null指针。通过检查mysql_error()是否返回非空字符串,mysql_errno()是否返回非0值,或mysql_field_count()是否返回0,可以检查是否出现了错误。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;h4 id="6释放结果集"&gt;6,释放结果集&lt;/h4&gt;&nbsp;</p>
<p>&nbsp;&lt;blockquote&gt;&nbsp;</p>
<p>&nbsp; &lt;p&gt;void mysql_free_result(MYSQL_RES *result)&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;/blockquote&gt;&nbsp;</p>
<p>&nbsp;&lt;h4 id="7获取查询的显示列的长度"&gt;7,获取查询的显示列的长度&lt;/h4&gt;&nbsp;</p>
<p>&nbsp;&lt;blockquote&gt;&nbsp;</p>
<p>&nbsp; &lt;p&gt;unsigned int mysql_num_fields(MYSQL_RES *result)&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;/blockquote&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;描述&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;返回结果集中的行数。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;注意,你可以从指向结果集的指针或指向连接句柄的指针获得行数。如果mysql_store_result()或mysql_use_result()返回NULL,应使用连接句柄(因而没有结果集指针)。在该情况下,可调用mysql_field_count()来判断mysql_store_result()是否生成了非空结果。这样,客户端程序就能采取恰当的行动,而不需要知道查询是否是SELECT语句(或类似SELECT的语句)。在下面的示例中,介绍了执行该操作的方式。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;h4 id="8获取列信息"&gt;8,获取列信息&lt;/h4&gt;&nbsp;</p>
<p>&nbsp;&lt;blockquote&gt;&nbsp;</p>
<p>&nbsp; &lt;p&gt;MYSQL_FIELD *mysql_fetch_field(MYSQL_RES *result)&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;/blockquote&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;描述&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;返回采用MYSQL_FIELD结构的结果集的列。重复调用该函数,以检索关于结果集中所有列的信息。未剩余字段时,mysql_fetch_field()返回NULL。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;每次执行新的SELECT查询时,将复位mysql_fetch_field(),以返回关于第1个字段的信息。调用mysql_field_seek()也会影响mysql_fetch_field()返回的字段。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;如果调用了mysql_query()以在表上执行SELECT,但未调用mysql_store_result(),如果调用了mysql_fetch_field()以请求BLOB字段的长度,MySQL将返回默认的Blob长度(8KB)。之所以选择8KB是因为MySQL不知道BLOB的最大长度。应在日后使其成为可配置的。一旦检索了结果集,field-&amp;gt;max_length将包含特定查询中该列的最大值的长度。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;返回值&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;当前列的MYSQL_FIELD结构。如果未剩余任何列,返回NULL。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;h4 id="9取出一行信息"&gt;9,取出一行信息&lt;/h4&gt;&nbsp;</p>
<p>&nbsp;&lt;blockquote&gt;&nbsp;</p>
<p>&nbsp; &lt;p&gt;MYSQL_ROW mysql_fetch_row(MYSQL_RES *result)&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;/blockquote&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;描述&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;检索结果集的下一行。在mysql_store_result()之后使用时,如果没有要检索的行,mysql_fetch_row()返回NULL。在mysql_use_result()之后使用时,如果没有要检索的行或出现了错误,mysql_fetch_row()返回NULL。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;行内值的数目由mysql_num_fields(result)给出。如果行中保存了调用mysql_fetch_row()返回的值,将按照row[0]到row[mysql_num_fields(result)-1],访问这些值的指针。行中的NULL值由NULL指针指明。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;可以通过调用mysql_fetch_lengths()来获得行中字段值的长度。对于空字段以及包含NULL的字段,长度为0。通过检查字段值的指针,能够区分它们。如果指针为NULL,字段为NULL,否则字段为空。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;返回值&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;下一行的MYSQL_ROW结构。如果没有更多要检索的行或出现了错误,返回NULL。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;h4 id="10显示受影响的行数"&gt;10,显示受影响的行数&lt;/h4&gt;&nbsp;</p>
<p>&nbsp;&lt;blockquote&gt;&nbsp;</p>
<p>&nbsp; &lt;p&gt;my_ulonglong mysql_affected_rows(MYSQL *mysql)&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;/blockquote&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;描述&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;返回上次UPDATE更改的行数,上次DELETE删除的行数,或上次INSERT语句插入的行数。对于UPDATE、DELETE或INSERT语句,可在mysql_query()后立刻调用。对于SELECT语句,mysql_affected_rows()的工作方式与mysql_num_rows()类似。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;返回值&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;大于0的整数表明受影响或检索的行数。&ldquo;0&rdquo;表示UPDATE语句未更新记录,在查询中没有与WHERE匹配的行,或未执行查询。&ldquo;-1&rdquo;表示查询返回错误,或者,对于SELECT查询,在调用mysql_store_result()之前调用了mysql_affected_rows()。由于mysql_affected_rows()返回无符号值,通过比较返回值和&ldquo;(my_ulonglong)-1&rdquo;或等效的&ldquo;(my_ulonglong)~0&rdquo;,检查是否为&ldquo;-1&rdquo;。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;pre class="brush:sql;"&gt;</p>
<p>#include&nbsp;</p>
<p>&nbsp; &lt;stdio.h&gt;</p>
<p>&nbsp; &nbsp;</p>
<p>#include&nbsp;</p>
<p>&nbsp; &nbsp;&lt;stdlib.h&gt;</p>
<p>&nbsp; &nbsp; &nbsp;#include&nbsp;</p>
<p>&nbsp; &nbsp; &lt;string.h&gt;</p>
<p>&nbsp; &nbsp; &nbsp; #include&nbsp;</p>
<p>&nbsp; &nbsp; &nbsp;&lt;mysql.h&gt;</p>
<p>&nbsp; &nbsp; &nbsp; &nbsp;#include&nbsp;</p>
<p>&nbsp; &nbsp; &nbsp; &lt;unistd.h&gt;</p>
<p>&nbsp; &nbsp; &nbsp; &nbsp; #define _USER_ &amp;quot;root&amp;quot; //用户名 #define _HOST_ &amp;quot;127.0.0.1&amp;quot; //host #define _PASSWD_ &amp;quot;123&amp;quot; //root 用户名密码 #define _DB_ &amp;quot;scott&amp;quot; //库名 #define _PORT_ 3306 //port //打印信息 结果集 void show_information(MYSQL_RES * res, MYSQL *mysql) { int i; MYSQL_ROW row; // //unsigned long *lengths; unsigned int num_fields; MYSQL_FIELD *field; //字段名 // 数据的长度unsigned int mysql_num_fields(MYSQL_RES *result) num_fields = mysql_num_fields(res); //返回列长unsigned long *mysql_fetch_lengths(MYSQL_RES *result) //lengths = mysql_fetch_lengths(res); printf(&amp;quot;num_fields = [%d]\n&amp;quot;, num_fields); //字段名 for (i = 0; i &amp;lt; num_fields, field = mysql_fetch_field(res); i++) { printf(&amp;quot; %s\t&amp;quot;, field-&amp;gt;name); } printf(&amp;quot;\n&amp;quot;); printf(&amp;quot;--------------------------------------------------------------\n&amp;quot;); while ((row = mysql_fetch_row(res))) { for (i = 0; i &amp;lt; num_fields; i++) { printf(&amp;quot;%s \t&amp;quot;, row[i] ? row[i] : NULL); } printf(&amp;quot;\n&amp;quot;); } //释放结果集 mysql_free_result(res); printf(&amp;quot;--------------------------------------------------------------\n&amp;quot;); //显示受影响的行数 printf(&amp;quot; %ld rows in set\n&amp;quot;, (long) mysql_affected_rows(mysql)); } int main(int argc, char *argv[]) { int ret, i; MYSQL *mysql; MYSQL_RES * res; char strsql[512] = { 0}; //1,mysql_init 初始化 mysql = mysql_init(NULL); if (mysql == NULL) { printf(&amp;quot;mysql_init error\n&amp;quot;); return -1; } //2,mysql_real_connect链接 mysql = mysql_real_connect(mysql, _HOST_, _USER_, _PASSWD_, _DB_, 0, NULL, 0); if (mysql == NULL) { printf(&amp;quot;mysql_real_connect error\n&amp;quot;); return -1; } printf(&amp;quot;connect mysql ok\n&amp;quot;); //处理字符问题的函数 if ( mysql_set_character_set(mysql, &amp;quot;utf8&amp;quot;) != 0) { printf(&amp;quot; mysql_set_character_set error\n&amp;quot;); mysql_close(mysql); exit(1); } //===========================输入sql语句====================== while (1) { memset(strsql, 0x00, sizeof(strsql)); write(STDOUT_FILENO, &amp;quot;yoursql&amp;gt;&amp;quot;, ; //读取client输入的sql字符串 read(STDIN_FILENO, strsql, sizeof(strsql)); //退出的处理 if (strncasecmp(strsql, &amp;quot;quit&amp;quot;, 4) == 0) { printf(&amp;quot;client 退出处理\n&amp;quot;); break; } //输入sql的 ret = mysql_query(mysql, strsql); if (ret) { printf(&amp;quot;mysql_query error\n&amp;quot;); continue; } res = mysql_store_result(mysql); //有结果集的处理 if (res != NULL) { show_information(res, mysql); } else { //显示受影响的行数 printf(&amp;quot; Query OK, %ld row affected\n&amp;quot;,(long) mysql_affected_rows(mysql)); } } // char sqlstr[] = &amp;quot;select *from emp&amp;quot;; // //查询语句int mysql_query(MYSQL *mysql, const char *query) // ret = mysql_query(mysql, sqlstr); // if (ret) { // printf(&amp;quot;mysql_query error\n&amp;quot;); // return -1; // } // // //查询的结果集MYSQL_RES *mysql_store_result(MYSQL *mysql) // res = mysql_store_result(mysql); //MYSQL_ROW mysql_fetch_row(MYSQL_RES *result) // if ( res != NULL) { // show_information(res); // // 数据的长度unsigned int mysql_num_fields(MYSQL_RES *result) // num_fields = mysql_num_fields(res); // //返回列长unsigned long *mysql_fetch_lengths(MYSQL_RES *result) // //lengths = mysql_fetch_lengths(res); // printf(&amp;quot;num_fields = [%d]\n&amp;quot;, num_fields); // //字段名 // for (i = 0; i &amp;lt; num_fields, field = mysql_fetch_field(res); i++) { // printf(&amp;quot; %s\t&amp;quot;, field-&amp;gt;name); // } // printf(&amp;quot;\n&amp;quot;); // while (row = mysql_fetch_row(res)) { // // for (i = 0; i &amp;lt; num_fields; i++) { // printf(&amp;quot;%s \t&amp;quot;, row[i]); // } // printf(&amp;quot;\n&amp;quot;); // } // //释放结果集 // mysql_free_result(res); // } //关闭mysql mysql_close(mysql); return 0; }&nbsp;</p>
<p>&nbsp; &nbsp; &nbsp; &lt;/unistd.h&gt;</p>
<p>&nbsp; &nbsp; &nbsp;&lt;/mysql.h&gt;</p>
<p>&nbsp; &nbsp; &lt;/string.h&gt;</p>
<p>&nbsp; &nbsp;&lt;/stdlib.h&gt;</p>
<p>&nbsp; &lt;/stdio.h&gt;&lt;/pre&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;&lt;img alt="这里写图片描述" src="/uploadfile/Collfiles/20171118/2017111809064163.gif" /&gt;&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;h3 id="二sql预处理-防止注入和增加效率"&gt;二,SQL预处理 防止注入和增加效率&lt;/h3&gt;&nbsp;</p>
<p>&nbsp;&lt;h4 id="1插入预处理"&gt;1,插入预处理&lt;/h4&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;流程图&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;&lt;img alt="这里写图片描述" src="/uploadfile/Collfiles/20171118/2017111809064167.png" /&gt;&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;&lt;img alt="这里写图片描述" src="/uploadfile/Collfiles/20171118/2017111809064169.png" /&gt;&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;原理&lt;br /&gt; &lt;img alt="这里写图片描述" src="/uploadfile/Collfiles/20171118/20171118090651117.png" /&gt;&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;h5 id="①api介绍"&gt;①api介绍&lt;/h5&gt;&nbsp;</p>
<p>&nbsp;&lt;h6 id="1预处理初始化"&gt; 1,预处理初始化&lt;/h6&gt;&nbsp;</p>
<p>&nbsp;&lt;blockquote&gt;&nbsp;</p>
<p>&nbsp; &lt;p&gt;MYSQL_STMT *mysql_stmt_init(MYSQL *mysql)&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;/blockquote&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;描述&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;创建MYSQL_STMT句柄。对于该句柄,应使用mysql_stmt_close(MYSQL_STMT *)释放。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;返回值&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;成功时,返回指向MYSQL_STMT结构的指针。如果内存溢出,返回NULL。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;h6 id="2插入预处理语句"&gt; 2,插入预处理语句&lt;/h6&gt;&nbsp;</p>
<p>&nbsp;&lt;blockquote&gt;&nbsp;</p>
<p>&nbsp; &lt;p&gt;int mysql_stmt_prepare(MYSQL_STMT *stmt, const char *query, unsigned long length)&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;/blockquote&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;描述&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;给定mysql_stmt_init()返回的语句句柄,准备字符串查询指向的SQL语句,并返回状态值。字符串长度应由&ldquo;length&rdquo;参量给出。字符串必须包含1条SQL语句。不应为语句添加终结用分号(&lsquo;;&rsquo;)或\g。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;通过将问号字符&ldquo;?&rdquo;嵌入到SQL字符串的恰当位置,应用程序可包含SQL语句中的一个或多个参数标记符。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;标记符仅在SQL语句中的特定位置时才是合法的。例如,它可以在INSERT语句的VALUES()列表中(为行指定列值),或与WHERE子句中某列的比较部分(用以指定比较值)。但是,对于ID(例如表名或列名),不允许使用它们,不允许指定二进制操作符(如等于号&ldquo;=&rdquo;)的操作数。后一个限制是有必要的,原因在于,无法确定参数类型。一般而言,参数仅在DML(数据操作语言)语句中才是合法的,在DDL(数据定义语言)语句中不合法。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;执行语句之前,必须使用mysql_stmt_bind_param(),将参数标记符与应用程序变量绑定在一起。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;返回值&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;如果成功处理了语句,返回0。如果出现错误,返回非0值。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;h6 id="3获取参数"&gt; 3,获取参数&lt;/h6&gt;&nbsp;</p>
<p>&nbsp;&lt;blockquote&gt;&nbsp;</p>
<p>&nbsp; &lt;p&gt;unsigned long mysql_stmt_param_count(MYSQL_STMT *stmt)&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;/blockquote&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;描述&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;返回预处理语句中参数标记符的数目。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;返回值&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;表示语句中参数数目的无符号长整数。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;h6 id="4参数的绑定"&gt; 4,参数的绑定&lt;/h6&gt;&nbsp;</p>
<p>&nbsp;&lt;blockquote&gt;&nbsp;</p>
<p>&nbsp; &lt;p&gt;my_bool mysql_stmt_bind_param(MYSQL_STMT *stmt, MYSQL_BIND *bind)&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;/blockquote&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;描述&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;mysql_stmt_bind_param()用于为SQL语句中的参数标记符绑定数据,以传递给mysql_stmt_prepare()。它使用MYSQL_BIND结构来提供数据。&ldquo;bind&rdquo;是MYSQL_BIND结构的某一数组的地址。按照客户端库的预期,对于查询中出现的每个&ldquo;?&rdquo;参数标记符,数组中均包含1个元素。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;假定你准备了下述语句:&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;INSERT INTO mytbl VALUES(?,?,?)&lt;br /&gt; 绑定参数时,MYSQL_BIND结构的数组包含3个元素,并能声明如下:&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;MYSQL_BIND bind[3];&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;h6 id="5预处理执行"&gt; 5,预处理执行&lt;/h6&gt;&nbsp;</p>
<p>&nbsp;&lt;blockquote&gt;&nbsp;</p>
<p>&nbsp; &lt;p&gt;int mysql_stmt_execute(MYSQL_STMT *stmt)&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;/blockquote&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;描述&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;mysql_stmt_execute()执行与语句句柄相关的预处理查询。在该调用期间,将当前绑定的参数标记符的值发送到服务器,服务器用新提供的数据替换标记符。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;如果语句是UPDATE、DELETE或INSERT,通过调用mysql_stmt_affected_rows(),可发现更改、删除或插入的总行数。如果这是诸如SELECT等能生成结果集的语句,调用任何其他能导致查询处理的函数之前,必须调用mysql_stmt_fetch()来获取数据。关于如何获取结果的更多信息,请参见25.2.7.11节,&ldquo;mysql_stmt_fetch()&rdquo;。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;对于生成结果集的语句,执行语句之前,可通过调用mysql_stmt_attr_set(),请求mysql_stmt_execute()为语句打开光标。如果多次执行某一语句,在打开新的光标前,mysql_stmt_execute()将关闭任何已打开的光标。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;返回值&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;如果执行成功,返回0。如果出现错误,返回非0值。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;h6 id="6返回预处理的行数"&gt; 6,返回预处理的行数&lt;/h6&gt;&nbsp;</p>
<p>&nbsp;&lt;blockquote&gt;&nbsp;</p>
<p>&nbsp; &lt;p&gt;my_ulonglong mysql_stmt_affected_rows(MYSQL_STMT *stmt)&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;/blockquote&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;描述&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;返回上次执行语句更改、删除或插入的总行数。对于UPDATE、DELETE或INSERT语句,可在mysql_stmt_execute()之后立刻调用它们。对于SELECT语句,mysql_stmt_affected_rows()的工作方式类似于mysql_num_rows()。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;返回值&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;大于0的整数指明了受影响或检索的行数。对于UPDATE语句,&ldquo;0&rdquo;表明未更新任何记录,在查询中没有与WHERE子句匹配的行,或尚未执行任何查询。&ldquo;-1&rdquo;表明返回了错误,或对SELECT查询,在调用mysql_stmt_store_result()之前调用了mysql_stmt_affected_rows()。由于mysql_stmt_affected_rows()返回无符号值,可通过比较返回值和&ldquo;(my_ulonglong)-1&rdquo;(或等效的&ldquo;(my_ulonglong)~0&rdquo;),检查&ldquo;-1&rdquo;。&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;pre class="brush:sql;"&gt;</p>
<p>//预处理方式api处理 -- insert&nbsp;</p>
<p>#include&nbsp;</p>
<p>&nbsp; &lt;stdio.h&gt;</p>
<p>&nbsp; &nbsp;</p>
<p>#include &amp;quot;mysql.h&amp;quot;</p>
<p>#include&nbsp;</p>
<p>&nbsp; &nbsp;&lt;stdlib.h&gt;</p>
<p>&nbsp; &nbsp; &nbsp;#include&nbsp;</p>
<p>&nbsp; &nbsp; &lt;string.h&gt;</p>
<p>&nbsp; &nbsp; &nbsp; #define _HOST_ &amp;quot;localhost&amp;quot; //主机 #define _USER_ &amp;quot;root&amp;quot; //mysql用户,非主机 #define _PASSWD_ &amp;quot;123&amp;quot; //密码 #define _DBNAME_ &amp;quot;scott&amp;quot; //库名 #define STRING_SIZE 50 #define DROP_SAMPLE_TABLE &amp;quot;DROP TABLE IF EXISTS test_table&amp;quot; // if EXISTS 好处 是如果表不存在,执行不会报错 #define CREATE_SAMPLE_TABLE &amp;quot;CREATE TABLE test_table(col1 INT,\ col2 VARCHAR(40),\ col3 SMALLINT,\ col4 TIMESTAMP)&amp;quot; #define INSERT_SAMPLE &amp;quot;INSERT INTO test_table(col1,col2,col3) VALUES(?,?,?)&amp;quot; void prepare_insert(MYSQL *mysql); int main() { //1.初始化 MYSQL * mysql = NULL; mysql = mysql_init(NULL) ; if(mysql == NULL ) { printf(&amp;quot;mysql init err\n&amp;quot;); exit(1); } //2.连接 mysql = mysql_real_connect(mysql, _HOST_,_USER_, _PASSWD_,_DBNAME_, 0, NULL,0); if(mysql == NULL) { printf(&amp;quot;mysql_real_connect connect err\n&amp;quot;); exit(1); } printf(&amp;quot;welcome to mysql \n&amp;quot;); prepare_insert(mysql); //3.关闭 mysql_close(mysql); return 0; } void prepare_insert(MYSQL *mysql) { MYSQL_STMT *stmt;//预处理的句柄 -- 标识进程内唯一的一个预处理的sql MYSQL_BIND bind[3];//绑定变量 my_ulonglong affected_rows; int param_count; short small_data; int int_data; char str_data[STRING_SIZE]; unsigned long str_length; my_bool is_null; if (mysql_query(mysql, DROP_SAMPLE_TABLE))//删除表 { fprintf(stderr, &amp;quot; DROP TABLE failed\n&amp;quot;); fprintf(stderr, &amp;quot; %s\n&amp;quot;, mysql_error(mysql)); exit(0); } if (mysql_query(mysql, CREATE_SAMPLE_TABLE))//创建表 { fprintf(stderr, &amp;quot; CREATE TABLE failed\n&amp;quot;); fprintf(stderr, &amp;quot; %s\n&amp;quot;, mysql_error(mysql)); exit(0); } /* Prepare an INSERT query with 3 parameters */ /* (the TIMESTAMP column is not named; the server */ /* sets it to the current date and time) */ stmt = mysql_stmt_init(mysql); //预处理的初始化 if (!stmt) { fprintf(stderr, &amp;quot; mysql_stmt_init(), out of memory\n&amp;quot;); exit(0); } if (mysql_stmt_prepare(stmt, INSERT_SAMPLE, strlen(INSERT_SAMPLE))) //insert 语句 的预处理 { fprintf(stderr, &amp;quot; mysql_stmt_prepare(), INSERT failed\n&amp;quot;); fprintf(stderr, &amp;quot; %s\n&amp;quot;, mysql_stmt_error(stmt)); exit(0); } fprintf(stdout, &amp;quot; prepare, INSERT successful\n&amp;quot;); /* Get the parameter count from the statement */ param_count= mysql_stmt_param_count(stmt);//获得参数个数 fprintf(stdout, &amp;quot; total parameters in INSERT: %d\n&amp;quot;, param_count); if (param_count != 3) /* validate parameter count */ { fprintf(stderr, &amp;quot; invalid parameter count returned by MySQL\n&amp;quot;); exit(0); } /* Bind the data for all 3 parameters */ memset(bind, 0, sizeof(bind)); /* INTEGER PARAM */ /* This is a number type, so there is no need to specify buffer_length */ bind[0].buffer_type= MYSQL_TYPE_LONG;//对应int类型 bind[0].buffer= (char *)&amp;amp;int_data;//内存地址的映射 bind[0].is_null= 0; bind[0].length= 0; /* STRING PARAM */ bind[1].buffer_type= MYSQL_TYPE_STRING; bind[1].buffer= (char *)str_data;//char 100 bind[1].buffer_length= STRING_SIZE; bind[1].is_null= 0; bind[1].length= &amp;amp;str_length; /* SMALLINT PARAM */ bind[2].buffer_type= MYSQL_TYPE_SHORT; bind[2].buffer= (char *)&amp;amp;small_data; bind[2].is_null= &amp;amp;is_null;//是否为null的指示器 bind[2].length= 0; /* Bind the buffers */ if (mysql_stmt_bind_param(stmt, bind)) //绑定变量 参数绑定 { fprintf(stderr, &amp;quot; mysql_stmt_bind_param() failed\n&amp;quot;); fprintf(stderr, &amp;quot; %s\n&amp;quot;, mysql_stmt_error(stmt)); exit(0); } //第一波赋值 int_data= 10; /* integer */ strncpy(str_data, &amp;quot;MySQL&amp;quot;, STRING_SIZE); /* string */ str_length= strlen(str_data); //INSERT INTO test_table(col1,col2,col3) VALUES(10,'MySQL',null) /* INSERT SMALLINT data as NULL */ is_null= 1;//指示插入的第三个字段是否为null //insert into test_table(col1,col2,col3) values(10,'MySQL',null); /* Execute the INSERT statement - 1*/ if (mysql_stmt_execute(stmt)) //预处理的执行,第一次执行 { fprintf(stderr, &amp;quot; mysql_stmt_execute(), 1 failed\n&amp;quot;); fprintf(stderr, &amp;quot; %s\n&amp;quot;, mysql_stmt_error(stmt)); exit(0); } /* Get the total number of affected rows */ affected_rows= mysql_stmt_affected_rows(stmt);//预处理的影响条数 fprintf(stdout, &amp;quot; total affected rows(insert 1): %lu\n&amp;quot;, (unsigned long) affected_rows); if (affected_rows != 1) /* validate affected rows */ { fprintf(stderr, &amp;quot; invalid affected rows by MySQL\n&amp;quot;); exit(0); } //第二波赋值 int_data= 1000; strncpy(str_data, &amp;quot;The most popular Open Source database&amp;quot;, STRING_SIZE); str_length= strlen(str_data); small_data= 1000; /* smallint */ is_null= 1; /* reset */ //INSERT INTO test_table(col1,col2,col3) VALUES(1000,'The most popular Open Source database',1000) //insert into test_table(col1,col2,col3) values(1000,'The most popular Open Source database',1000); /* Execute the INSERT statement - 2*/ if (mysql_stmt_execute(stmt))//第二次执行 { fprintf(stderr, &amp;quot; mysql_stmt_execute, 2 failed\n&amp;quot;); fprintf(stderr, &amp;quot; %s\n&amp;quot;, mysql_stmt_error(stmt)); exit(0); } /* Get the total rows affected */ affected_rows= mysql_stmt_affected_rows(stmt); fprintf(stdout, &amp;quot; total affected rows(insert 2): %lu\n&amp;quot;, (unsigned long) affected_rows); if (affected_rows != 1) /* validate affected rows */ { fprintf(stderr, &amp;quot; invalid affected rows by MySQL\n&amp;quot;); exit(0); } /* Close the statement */ if (mysql_stmt_close(stmt)) { fprintf(stderr, &amp;quot; failed while closing the statement\n&amp;quot;); fprintf(stderr, &amp;quot; %s\n&amp;quot;, mysql_stmt_error(stmt)); exit(0); } }&nbsp;</p>
<p>&nbsp; &nbsp; &lt;/string.h&gt;</p>
<p>&nbsp; &nbsp;&lt;/stdlib.h&gt;</p>
<p>&nbsp; &lt;/stdio.h&gt;&lt;/pre&gt;&nbsp;</p>
<p>&nbsp;&lt;h4 id="2-查询预处理"&gt;2, 查询预处理&lt;/h4&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;流程图&lt;br /&gt; &lt;img alt="这里写图片描述" src="/uploadfile/Collfiles/20171118/20171118090651118.png" /&gt;&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;h5 id="api介绍"&gt;api介绍&lt;/h5&gt;&nbsp;</p>
<p>&nbsp;&lt;blockquote&gt;&nbsp;</p>
<p>&nbsp; &lt;p&gt;MYSQL_RES *mysql_stmt_param_metadata(MYSQL_STMT *stmt)&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;/blockquote&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;提前指定结果集的操作&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;pre class="brush:sql;"&gt;</p>
<p>//select *from dept; 查询语句的使用</p>
<p>#include&nbsp;</p>
<p>&nbsp; &lt;stdio.h&gt;</p>
<p>&nbsp; &nbsp;</p>
<p>#include&nbsp;</p>
<p>&nbsp; &nbsp;&lt;stdlib.h&gt;</p>
<p>&nbsp; &nbsp; &nbsp;#include&nbsp;</p>
<p>&nbsp; &nbsp; &lt;string.h&gt;</p>
<p>&nbsp; &nbsp; &nbsp; #include&nbsp;</p>
<p>&nbsp; &nbsp; &nbsp;&lt;mysql.h&gt;</p>
<p>&nbsp; &nbsp; &nbsp; &nbsp;#define _USER_ &amp;quot;root&amp;quot; //用户名 #define _HOST_ &amp;quot;127.0.0.1&amp;quot; //host #define _PASSWD_ &amp;quot;123&amp;quot; //root 用户名密码 #define _DB_ &amp;quot;scott&amp;quot; //库名 #define _PORT_ 3306 //port //============================stmt ====================================== #define STRING_SIZE 50 //mysql 查询语句 #define SELECT_SAMPLE &amp;quot;SELECT deptno, dname, loc FROM dept&amp;quot; void seach_information(MYSQL *mysql){ int i, count = 0;; MYSQL_STMT *stmt; // MYSQL_BIND bind[3]; //条件变量 MYSQL_RES *prepare_meta_result; //结果集 unsigned long length[3]; int param_count, column_count, row_count; int int_data; //序号 char str_name[STRING_SIZE]; //姓名 char str_loc[STRING_SIZE]; my_bool is_null[3]; //参数的控制 my_ulonglong row_unm; //===========================init start========================= //初始化sql预处理语句 stmt = mysql_stmt_init(mysql); if (!stmt) { fprintf(stderr, &amp;quot; mysql_stmt_init(), out of memory\n&amp;quot;); exit(0); } //绑定参数my_bool mysql_stmt_bind_param(MYSQL_STMT *stmt, MYSQL_BIND *bind) //mysql_stmt_bind_param(stmt, bind); if (mysql_stmt_prepare(stmt, SELECT_SAMPLE, strlen(SELECT_SAMPLE))) { fprintf(stderr, &amp;quot; mysql_stmt_prepare(), SELECT failed\n&amp;quot;); fprintf(stderr, &amp;quot; %s\n&amp;quot;, mysql_stmt_error(stmt)); exit(0); } fprintf(stdout, &amp;quot; prepare, SELECT successful\n&amp;quot;); fprintf(stdout, &amp;quot; total parameters in SELECT: %d\n&amp;quot;, param_count); param_count = mysql_stmt_param_count(stmt); if (param_count != 0) /* validate parameter count */ { fprintf(stderr, &amp;quot; invalid parameter count returned by MySQL\n&amp;quot;); exit(0); } prepare_meta_result = mysql_stmt_result_metadata(stmt); if (!prepare_meta_result) { fprintf(stderr, &amp;quot; mysql_stmt_result_metadata(), returned no meta information\n&amp;quot;); fprintf(stderr, &amp;quot; %s\n&amp;quot;, mysql_stmt_error(stmt)); exit(0); } column_count= mysql_num_fields(prepare_meta_result); fprintf(stdout, &amp;quot; total columns in SELECT statement: %d\n&amp;quot;, column_count); if (column_count != 3) /* validate column count */ { fprintf(stderr, &amp;quot; invalid column count returned by MySQL\n&amp;quot;); exit(0); } //mysql_stmt_execute(stmt); //发送占位符到mysql数据库上???? if (mysql_stmt_execute(stmt)) { fprintf(stderr, &amp;quot; mysql_stmt_execute(), failed\n&amp;quot;); fprintf(stderr, &amp;quot; %s\n&amp;quot;, mysql_stmt_error(stmt)); exit(0); } //初始化参数 memset(bind, 0, sizeof(bind)); /* INTEGER COLUMN */ bind[0].buffer_type= MYSQL_TYPE_LONG; bind[0].buffer= (char *)&amp;amp;int_data; bind[0].is_null= &amp;amp;is_null[0]; bind[0].length= &amp;amp;length[0]; //varchar -- MYSQL_TYPE_VAR_STRING /* name COLUMN */ bind[1].buffer_type= MYSQL_TYPE_VAR_STRING; bind[1].buffer= (char *)str_name; bind[1].buffer_length = STRING_SIZE; bind[1].is_null = &amp;amp;is_null[1]; bind[1].length = &amp;amp;length[1]; /* loc COLUMN */ bind[2].buffer_type= MYSQL_TYPE_VAR_STRING; bind[2].buffer= (char *)&amp;amp;str_loc; bind[2].buffer_length = STRING_SIZE; bind[2].is_null = &amp;amp;is_null[2]; bind[2].length = &amp;amp;length[2]; //绑定数据 mysql_stmt_bind_result(stmt, bind); mysql_stmt_store_result(stmt);// //init row row_count= 0; //查询的结果 row_unm = mysql_stmt_num_rows(stmt); //打印数据 //mysql_stmt_fetch(stmt); //mysql_stmt_fetch(stmt); printf(&amp;quot;row_unm = %ld\n&amp;quot;, row_unm); for (i = 0; i &amp;lt; row_unm; i++) { mysql_stmt_fetch(stmt); row_count++; fprintf(stdout, &amp;quot; row %d\n&amp;quot;, row_count); /* column 1 */ fprintf(stdout, &amp;quot; column1 (integer) : &amp;quot;); if (is_null[0]) fprintf(stdout, &amp;quot; NULL\n&amp;quot;); else fprintf(stdout, &amp;quot; %d(%ld)\n&amp;quot;, int_data, length[0]); /* column 2 */ fprintf(stdout, &amp;quot; column2 (string) : &amp;quot;); if (is_null[1]) fprintf(stdout, &amp;quot; NULL\n&amp;quot;); else fprintf(stdout, &amp;quot; %s(%ld)\n&amp;quot;, str_name, length[1]); /* column 3 */ fprintf(stdout, &amp;quot; column3 (string) : &amp;quot;); if (is_null[2]) fprintf(stdout, &amp;quot; NULL\n&amp;quot;); else fprintf(stdout, &amp;quot; %s(%ld)\n&amp;quot;, str_loc, length[2]); fprintf(stdout, &amp;quot;\n&amp;quot;); //break; } //释放内存 /* Validate rows fetched */ if (row_count != 10) { fprintf(stderr, &amp;quot; MySQL failed to return all rows\n&amp;quot;); exit(0); } /* Free the prepared result metadata */ mysql_free_result(prepare_meta_result); /* Close the statement */ mysql_stmt_close(stmt); } //===================================================================== int main(int argc, char *argv[]) { int ret, i; MYSQL *mysql; MYSQL_RES * res; MYSQL_ROW row; // //unsigned long *lengths; unsigned int num_fields; MYSQL_FIELD *field; //字段名 //1,mysql_init 初始化 mysql = mysql_init(NULL); if (mysql == NULL) { printf(&amp;quot;mysql_init error\n&amp;quot;); return -1; } //2,mysql_real_connect链接 mysql = mysql_real_connect(mysql, _HOST_, _USER_, _PASSWD_, _DB_, 0, NULL, 0); if (mysql == NULL) { printf(&amp;quot;mysql_real_connect error\n&amp;quot;); return -1; } printf(&amp;quot;connect mysql ok\n&amp;quot;); //设置一下字符编码utf8 if (mysql_set_character_set(mysql, &amp;quot;utf8&amp;quot;)) { printf(&amp;quot; mysql_set_character_set error\n&amp;quot;); return -1; } seach_information(mysql); // char sqlstr[] = &amp;quot;select *from emp&amp;quot;; // //查询语句int mysql_query(MYSQL *mysql, const char *query) // ret = mysql_query(mysql, sqlstr); // if (ret) { // printf(&amp;quot;mysql_query error\n&amp;quot;); // return -1; // } // // //查询的结果集MYSQL_RES *mysql_store_result(MYSQL *mysql) // res = mysql_store_result(mysql); // // //MYSQL_ROW mysql_fetch_row(MYSQL_RES *result) // if ( res != NULL) { // // 数据的长度unsigned int mysql_num_fields(MYSQL_RES *result) // num_fields = mysql_num_fields(res); // //返回列长unsigned long *mysql_fetch_lengths(MYSQL_RES *result) // //lengths = mysql_fetch_lengths(res); // printf(&amp;quot;num_fields = [%d]\n&amp;quot;, num_fields); // //字段名 // for (i = 0; i &amp;lt; num_fields, field = mysql_fetch_field(res); i++) { // printf(&amp;quot; %s\t&amp;quot;, field-&amp;gt;name); // } // printf(&amp;quot;\n&amp;quot;); // while (row = mysql_fetch_row(res)) { // // for (i = 0; i &amp;lt; num_fields; i++) { // printf(&amp;quot;%s \t&amp;quot;, row[i]); // } // printf(&amp;quot;\n&amp;quot;); // } // //释放结果集 // mysql_free_result(res); // } //关闭mysql mysql_close(mysql); return 0; }&nbsp;</p>
<p>&nbsp; &nbsp; &nbsp;&lt;/mysql.h&gt;</p>
<p>&nbsp; &nbsp; &lt;/string.h&gt;</p>
<p>&nbsp; &nbsp;&lt;/stdlib.h&gt;</p>
<p>&nbsp; &lt;/stdio.h&gt;&lt;/pre&gt;&nbsp;</p>
<p>&nbsp;&lt;p&gt;&lt;img alt="这里写图片描述" src="/uploadfile/Collfiles/20171118/20171118090653119.gif" /&gt;&lt;/p&gt;&nbsp;</p>
<p>&nbsp;&lt;h3 id="事物的介绍"&gt;事物的介绍&lt;/h3&gt;&nbsp;</p>
<p>&nbsp;&lt;pre class="brush:sql;"&gt;</p>
<p>//mysql中的事务</p>
<p>#include&nbsp;</p>
<p>&nbsp; &lt;stdio.h&gt;</p>
<p>&nbsp; &nbsp;</p>
<p>#include&nbsp;</p>
<p>&nbsp; &nbsp;&lt;stdlib.h&gt;</p>
<p>&nbsp; &nbsp; &nbsp;#include&nbsp;</p>
<p>&nbsp; &nbsp; &lt;string.h&gt;</p>
<p>&nbsp; &nbsp; &nbsp; #include &amp;quot;mysql.h&amp;quot; #define SET_TRAN &amp;quot;SET AUTOCOMMIT=0&amp;quot; //手动commit &mdash;&mdash;&mdash;&mdash;手动commit #define UNSET_TRAN &amp;quot;SET AUTOCOMMIT=1&amp;quot; //自动commit #define _HOST_ &amp;quot;127.0.0.1&amp;quot; #define _USER_ &amp;quot;root&amp;quot; #define _PASSWD_ &amp;quot;123&amp;quot; #define _DBNAME_ &amp;quot;scott&amp;quot; //设置事务为手动提交 int mysql_OperationTran(MYSQL *mysql) { //--开启事务 int ret = mysql_query(mysql, &amp;quot;start transaction&amp;quot;); //开启一次事务 start transaction if (ret != 0) { printf(&amp;quot;mysql_OperationTran query start err: %s\n&amp;quot;, mysql_error(mysql)); return ret; } //--设置事务为手动提交 ret = mysql_query(mysql, SET_TRAN); //set autocommmit = 0 if (ret != 0) { printf(&amp;quot;mysql_OperationTran query set err: %s\n&amp;quot;, mysql_error(mysql)); return ret; } return ret; } //设置事务为自动提交 int mysql_AutoTran(MYSQL *mysql) { //--开启事务 int ret = mysql_query(mysql, &amp;quot;start transaction&amp;quot;); if (ret != 0) { printf(&amp;quot;mysql_AutoTran query start err: %s\n&amp;quot;, mysql_error(mysql)); return ret; } //--设置事务为自动提交 ret = mysql_query(mysql, UNSET_TRAN); //&amp;quot;set autocommit = 1&amp;quot; if (ret != 0) { printf(&amp;quot;mysql_AutoTran query set err: %s\n&amp;quot;, mysql_error(mysql)); return ret; } return ret; } //执行commit,手动提交事务 int mysql_Commit(MYSQL *mysql) { int ret = mysql_query(mysql, &amp;quot;COMMIT&amp;quot;); //提交 if (ret != 0) { printf(&amp;quot;commit err: %s\n&amp;quot;, mysql_error(mysql)); return ret; } return ret; } //执行rollback,回滚事务 int mysql_Rollback(MYSQL *mysql) { int ret = mysql_query(mysql, &amp;quot;ROLLBACK&amp;quot;); if (ret != 0) { printf(&amp;quot;rollback err: %s\n&amp;quot;, mysql_error(mysql)); return ret; } return ret; } #define DROP_SAMPLE_TABLE &amp;quot;DROP TABLE IF EXISTS test_table&amp;quot; #define CREATE_SAMPLE_TABLE &amp;quot;CREATE TABLE test_table(col1 INT,\ col2 VARCHAR(10),\ col3 VARCHAR(10))&amp;quot; #define sql01 &amp;quot;INSERT INTO test_table(col1,col2,col3) VALUES(10, 'AAA', 'A1')&amp;quot; #define sql02 &amp;quot;INSERT INTO test_table(col1,col2,col3) VALUES(20, 'BBB', 'B2')&amp;quot; #define sql03 &amp;quot;INSERT INTO test_table(col1,col2,col3) VALUES(30, 'CCC', 'C3')&amp;quot; #define sql04 &amp;quot;INSERT INTO test_table(col1,col2,col3) VALUES(40, 'DDD', 'D4')&amp;quot; int main(void) { int ret = 0; MYSQL *mysql = mysql_init(NULL); mysql = mysql_real_connect(mysql, _HOST_, _USER_, _PASSWD_, _DBNAME_, 0, NULL, 0); if (mysql == NULL) { ret = mysql_errno(mysql); printf(&amp;quot;func mysql_real_connect() err:%d\n&amp;quot;, ret); return ret; } printf(&amp;quot; --- connect ok......\n&amp;quot;); //执行删除表 if (mysql_query(mysql, DROP_SAMPLE_TABLE)) { fprintf(stderr, &amp;quot; DROP TABLE failed\n&amp;quot;); fprintf(stderr, &amp;quot; %s\n&amp;quot;, mysql_error(mysql)); exit(0); } //执行创建表 if (mysql_query(mysql, CREATE_SAMPLE_TABLE)) { fprintf(stderr, &amp;quot; CREATE TABLE failed\n&amp;quot;); fprintf(stderr, &amp;quot; %s\n&amp;quot;, mysql_error(mysql)); exit(0); } ret = mysql_OperationTran(mysql); //开启事务,并修改事务属性为手动commit if (ret != 0) { printf(&amp;quot;mysql_OperationTran() err:%d\n&amp;quot;, ret); return ret; } ret = mysql_query(mysql, sql01); //向表中插入第一行数据 &lsquo;AAA&rsquo; if (ret != 0) { printf(&amp;quot;mysql_query() err:%d\n&amp;quot;, ret); return ret; } ret = mysql_query(mysql, sql02); //向表中插入第二行数据 &lsquo;BBB&rsquo; if (ret != 0) { printf(&amp;quot;mysql_query() err:%d\n&amp;quot;, ret); return ret; } ret = mysql_Commit(mysql); //手动提交事务 if (ret != 0) { printf(&amp;quot;mysql_Commit() err:%d\n&amp;quot;, ret); return ret; } //////////AAA BBB 进去了。 #if 1 ret = mysql_AutoTran(mysql); // =再次= 修改事务属性为【自动】commit if (ret != 0) { printf(&amp;quot;mysql_OperationTran() err:%d\n&amp;quot;, ret); return ret; } #else ret = mysql_OperationTran(mysql); // =再次= 修改事务属性为【手动】commit if (ret != 0) { printf(&amp;quot;mysql_OperationTran() err:%d\n&amp;quot;, ret); return ret; } #endif ret = mysql_query(mysql, sql03); //向表中插入第三行数据 &lsquo;CCC&rsquo; if (ret != 0) { printf(&amp;quot;mysql_query() err:%d\n&amp;quot;, ret); return ret; } ret = mysql_query(mysql, sql04); //向表中插入第四行数据 &lsquo;DDD&rsquo; if (ret != 0) { printf(&amp;quot;mysql_query() err:%d\n&amp;quot;, ret); return ret; } ret = mysql_Rollback(mysql); //直接rollback操作 if (ret != 0) { printf(&amp;quot;mysql_Rollback() err:%d\n&amp;quot;, ret); return ret; } //rollback操作是否能回退掉CCC、DDD的值,取决于事务属性。 mysql_close(mysql); return 0; }&nbsp;</p>
<p>&nbsp; &nbsp; &lt;/string.h&gt;</p>
<p>&nbsp; &nbsp;&lt;/stdlib.h&gt;</p>
<p>&nbsp; &lt;/stdio.h&gt;&lt;/pre&gt;&nbsp;</p>
<p>&lt;/div&gt;</p></div>

猜你喜欢

转载自sunmon.iteye.com/blog/2405830