linux程序设计――执行SQL语句(第八章)(一)

2015-07-24 06:33:25 · 作者: · 浏览: 6

8.3 使用C语言访问MySQL数据

4.处理返回的数据
MySQL返回两种类型的数据
1.从表中提取的信息,也就是列数据
2.关于数据的数据,即所谓的元数据(metadata),例如列名和类型.
mysql_field_count函数提供了一些关于查询结果的基本信息,它接受连接对象,并返回结果集中的字段(列)数目:
unsigned int mysql_field_count(MYSQL *connection);
在更通用的情况下,可以用mysql_field_count做其他事情,比如判断为何mysql_store_result的调用会失败.例如,如果mysql_store_result返回,但是mysql_field_count返回一个正数,可以推测出这个是一个提取错误.但是如果mysql_field_count返回0,则表示没有列可以提取,这可以解释为何存储结果会失败.对于通用查询处理模块或任何随意构造查询的情况,这个函数都非常有用.
编写程序select3.c输出数据
输出的数据不是很整洁,如果需要格式化的数据,则要同时得到MySQL返回的数据和元数据.使用mysql_fetch_field来同时将元数据和数据提取到一个新的结构中:
MYSQL_FIELD *mysql_fetch_field(MYSQL_RES *result);
需要重复调用此函数,直到返回表示数据结束的NULL值为止.然后,可以使用指向字段结构的数据的指针来得到关于列的信息.结构MYSQL_FIELD定义在mysql.h中.
MYSQL_FIELD中的成员 说明
char *name; 列名,为字符串
char *table; 列所属的表名.当一个查询要使用多个表时,特别有用.
char *def; 如果调用mysql_list_fields,它将包含该列的默认值
enum enum_field_types type; 列类型
unsigned int length; 列宽
unsigned int max_length; 如果使用mysql_store_result,它将包含以字节为单位的提取的最长列值的长度
unsigned int flags; 列定义的标志
unsigned int decimals; 小数点后的数字个数.
此外,使用下面的函数覆盖当前的字段编号:
MYSQL_FIELD_OFFSET mysql_field_seek(MYSQL_RES *result, MYSQL_FIELD_OFFSET offset);
该编号会随每次mysql_fetch_field调用而自动增加.如果给参数offset传递值0,将跳回第一列.
编写程序select4.c

8.3.4更多的函数

示例API调用 说明
char *mysql_get_client_info(void); 返回客户端使用的库的版本信息
char *mysql_get_host_info(MYSQL *connection); 返回服务器连接信息
char *mysql_get_server_info(MYSQL *connection); 返回当前连接的服务器的信息
char *mysql_info(MYSQL *connection); 返回最近执行的查询信息
int mysql_select_db(MYSQL *connection, const char *dbname);
如果用户拥有权限,则把默认数据库改为参数指定的数据库
int mysql_shutdown(MYSQL *connection, enum mysql_enum_shutdown_level);
如果用户拥有权限,则关闭连接的数据库服务器。

8.4 CD数据库应用程序

创建一个新的数据库,然后将其作为当前的数据库:
create database blpcd;
use blpcd;
只考虑数据的两种最重要的关系
首先,每张CD由不同数目的曲目组成,所以将把曲目数据存在一个独立于其他CD数据的表中。
其次,每位艺术家经常有多张专辑,所以将艺术家的信息存储一次,然后单独提取属于该艺术家的所有CD。

8.4.1 创建表

需要去确定表的实际结构。从主表——CD表开始,它保存大部分的信息。需要保存一个CD ID、一个分类号、一个标题以及一些标注。还需要一个来自artist表的ID号来表明是哪位艺术家制作了这张专辑。
artist表很简单,它仅仅保存艺术家的名字和一个唯一的艺术家ID号。track表也很简单,只需要一个CD ID来表明曲目属于哪张CD、一个曲目号和一个曲目标题。
首先是CD表:
CREATE TABLE cd(
id int auto_increment NOT NULL primary key,
title varchar(70) NOT NULL,
artist_id int NOT NULL,
catalogue varchar(30) NOT NULL,
notes varchar(100)
);
创建表cd,它包含下面一些列:
id列,包含一个自动增加的整数,它是表的主键
最长为70个字符的title
artist_id,在artist表中使用的一个整数
最长为30个字符的catalogue号
最长为100个字符的notes
只有notes列可以为NULL,其他列都必须包含值
其次是artist表:
CREATE TABLE artist(
id int auto_increment NOT NULL primary key,
name varchar(100) NOT NULL
);
最后是track表:
CREATE TABLE track(
cd_id int NOT NULL,
track_id int NOT NULL,
title varchar(70),
primary key(cd_id, track_id)
);
这次使用不同的方法来声明主键,track表的不同之处在于每张CD的ID会出现多次,而对于任何指定曲目的ID,例如曲目1,也会在不同CD中出现多次。但是,这两者的结合将永远是唯一的,所以将主键声明为这两列的结合,这被称为联合键。
将这些SQL语句存储在文件create_table.sql中,并将该文件保存在当前目录中,然后开始创建数据库以及其中的表。

8.4.2 添加数据

编写insert_data.sql文件,使用\.命令执行。
注意这个文件将删除数据库blpcd中所有的数据以确保脚本是干净的
此外,这个文件在ID字段中插入数值,而不是让auto_increment自动分配的。
使用mysql命令客户端和一些SQL语句来检查。首先,从数据库中选出每张专辑的头两首曲目:
SELECT artist.name, cd.title AS "CD Title", track.track_id, track.title AS "Track" FROM artist, cd, track WHERE artist.id = cd.artist_id AND track.cd_id = cd.id AND track.track_id < 3;
这条SQL语句的第一部分是:
SELECT artist.name, cd.title, track.track.id, track.title
它通过使用标记tablename.column来说明想要显示哪些列。
SELECT语句的AS部分