Python进阶第二课--数据库

1.前言

    上节内容介绍的关于GUI的知识,算是进阶的入门。在这里我们会介绍Python的数据库编程接口,这是一种连接SQL数据库的标准化方法,同时也会学习利用API来执行一些基本的SQL命令。在这里我们使用的数据库比较简单,是SQLite,当然我们也可以选择一些流行的商业数据库:Oracle或者SQL Server以及很多稳定的且被广泛使用的开源数据库:MySQL,PostgreSQL等等。

2.Python数据库编程接口

    在提供相同功能的不同模块之间进行切换的时的问题通常是它们的接口不同,为了解决Python中的各种数据库模块之间的兼容问题,现在已经通过一个标准的数据库编程接口 DB API。

2.1变量

    任何支持DB API的数据库模块都必须定义三个描述模块特性的全局变量,这样做是因为API设计的很灵活,以支持许多不同的底层机制,避免过多包装。三个全局变量如下:

  • apilevel:表示使用的Python DB API版本,它是一个字符串常量,提供正在使用的API版本号。如果这个变量不存在,那么该模块就不兼容该版本的API。
  • threadsafety:表示模块的线程安全等级,是个取值范围为0到3的整数。0表示线程之间完全不共享模块,而3表示模块完全是安全的,1表示线程本身可以共享模块,但不对连接共享。如果不使用多个线程,那么完全不用担心这个变量。
  • paramstyle:表示在SQL查询中使用的参数风格,在执行多次类似查询的时候,参数是如何评价到SQL查询中的。format表示标准的字符串格式化,可以在参数中进行拼接的地方插入%s。而值pyformat表示扩展的格式代码,用于字典拼接中。除了python的风格以外还有下面三种拼接方式:qmark意思是使用问号,而numeric表示使用:1或者:2格式的字段。而named表示:foobar这样的字段,其中foobar为参数名。

2.2异常

    当然API中也定义了一些异常类,以便尽可能错误处理。然而,这异常被定义成了一种层次结构,在except块中捕捉多种类型的异常。

    常见的异常如下所示:

异常 超类 描述
StandardError   所有异常的泛型基类
Warning StandardError 在非致命错误发生时引发
Error StandardError 所有错误条件的泛型超类
DataError Error 与数据库相关的问题,比如值超出范围
DatabaseError Error 与数据库相关的错误的基类

2.3连接和游标

    为了使用底层的数据库系统,必须首先连接到它。这个时候就需要在适当的环境下使用具名函数connect,该函数有多个参数,而具体用到那个参数取决于底层数据库的类型。API定义了以下关键字参数使用,并按表中给定的顺序传给它们,参数类型都应为字符串。下面为connect函数的常用参数:

参数名 描述 是否可选
dsn 数据源名称,给出该参数表示数据库依赖
user 用户名
password 用户密码
host 主机名
database 数据库名

    connect函数返回连接对象:

方法名 描述
close() 关闭连接后,连接对象和它的游标均不可用
commit() 如果支持的话就提交挂起的事务,否则不做任何事情
rollback() 回滚挂起的事务
cursor() 返回连接的游标

注意:rollback方法可能不可用,对不同的数据库类型而言是不通话的,不是所有数据库都支持事务。

cursor方法引入游标这个新的主题,通过游标执行SQL查询并检查结果,游标比连接支持更多的方法,而且可能在程序中更好用。下面分别给出游标的方法和特性。

游标方法:

名称 描述
callproc(name[,params]) 使用给定的名称和参数调用已命名的数据库过程
close()    关闭游标后,游标不可用
execute(oper[,params]) 执行一个SQL操作,可能带有参数
excutemany(oper,pseq) 对序列中的每个参数集执行SQL操作
fetchone() 把查询结果集中的下一行保存为序列,或者None
fetchmany([size]) 获取查询结果集中的多行,默认尺寸为arraysize
fetchall() 将所有的行作为序列的序列
nextset() 跳至下一个可用的结果集
setinputsizes(sizes) 为参数预先定义内存区域
setoutputsize(size,[,col]) 为获取的大数据值设定缓冲区尺寸

游标特性:

名称 描述
description 结果列描述的序列,只读
rowcount 结果中的行数,只读
arraysize fetchmany中返回的行数,默认为1

上述的内容会在后面的例子中涉及到,如果想查看更多可以参考官方文档哟。

2.4类型

    为了能与底层的SQL数据库更好地交互,需要对插入到列中的值得类型做出各种要求和限制,DB API定义了用于特殊类型的值和构造函数及常量。所有模块都要求实现下面提到的构造函数和特殊值,当然也有一些例外,一些模块可能不是完全按照要求去做。

    DB API构造函数和特殊值:

名称 描述
Date(year,month,day) 创建保存日期值的对象
Time(hour,minute,second)

创建保存时间值的对象

Timestamp(y,mon,d,n,min,s) 创建保存时间戳值的对象
DateFromTicks(ticks) 创建保存自新纪元以来秒数的对象
TimeFromTicks(ticks) 创建保存来自秒数的时间值的对象
TimestampFromTicks(ticks) 创建保存来自秒数的时间戳值的对象
Binary(string) 创建保存二进制字符串值的对象
STRING 描述基于字符串的列类型
BINARY 描述二进制列
NUMBER 描述数字列
DATETIME 描述日期/时间列
ROWID 描述ID列

3.SQLite

    为什么要采用SQLite,重要的原因之一就是它的一个包装(PySQLite)已经被包括在标准库内。除非是从源码开始编译Python,否则数据库模块本身也已经包含在内。下面来看一些例子理解一下:

3.1创建和填充表

    下面的程序创建了叫做foo的表和适当的字段,并且从ABBREV.txt中读取数据之后进行分析,然后通过调用curs.execute执行SQL的INSERT语句将文本字段中的值插入到数据库中。

import sqlite3

def convert(value):
    if value.startwith('~'):
        return value.strip('~')
    if not value:
        value='0'
        return float(value)

conn=sqlite3.connect('food.db')
curs=conn.cursor()

curs.execute('''
CREATE TABLE food(
    id    TEXT    PRIMARY KEY ,
    desc  TEXT
    water FLOAT
    protein FLOAT
    fat FLOAT
    ash FLOAT 
    carbs FLOAT
    fiber FLOAT
    suger FLOAT
)
''')

query='INSERT INTO food VALUES (?,?,?,?,?,?,?,?,?,?)'

for line in open('ABBREV.txt'):
    fields=line.split('^')
    vals=[convert(f) for f in fields[:field_count]]
    curs.execute(query,vals)
    
    
conn.commit()
conn.close()

当运行这个程序(将ABBREV.txt放在同一目录下)时,它会创建一个叫做food.db的文件,它包含数据库中的所有数据。

3.2搜索和处理结果

    使用数据库其实很简单。需要创建并且获得该链接的游标,使用execute方法来执行SQL查询,用fetchall等方法来获取提取查询结果。下面来看一个实际的例子:有关于食品数据库的查询程序

import sqlite3,sys

conn=sqlite3.connect('food.db')
curs=conn.cursor()

query='SELECT * FROM food WHERE %s ' % sys.argv[1]
print query
curs.execute(query)
names=[f[0] for f in curs.description]
for row in curs.fetchall(names,row):
    for pair in zip(names,row):
        print '%s: %s' %pair
    print 
    好了,关于数据库知识就先介绍到这里,在执行上述代码时候需要有真正存在的数据库为数据的获取提供一定的基础,否则代码执行将会出现错误。大家也可以尝试修改上面的代码来获取不同的数据。下一章节预告--网络编程。



    

猜你喜欢

转载自blog.csdn.net/qq_34454366/article/details/80748631