Python中操作关系数据库最直接的就是用DB-API了,流程一般是:连接、执行SQL语句、提交、断开。以MySQL为例,下面是各步骤的代码示例:

首先是连接:

Python代码
  1. % python
  2. >>> import MySQLdb
  3. >>> conn = MySQLdb.connect(host='localhost', user='root', passwd='python')

% python
>>> import MySQLdb
>>> conn = MySQLdb.connect(host='localhost', user='root', passwd='python')

接着便可以执行语句了,但在执行SQL语句前要先获取指针:

Python代码
  1. >>> curs = conn.cursor( )
  2. >>> curs.execute('create database peopledb')
  3. 1L
  4. >>> curs.execute('use peopledb')
  5. 0L
  6. >>> tblcmd = 'create table people (name char(30), job char(10), pay int(4))'
  7. >>> curs.execute(tblcmd)
  8. 0L

>>> curs = conn.cursor( )
>>> curs.execute('create database peopledb')
1L
>>> curs.execute('use peopledb')
0L
>>> tblcmd = 'create table people (name char(30), job char(10), pay int(4))'
>>> curs.execute(tblcmd)
0L

添加数据:

Python代码
  1. >>> curs.execute('insert people values (%s, %s, %s)', ('Bob', 'dev', 5000))
  2. 1L
  3. >>> curs.executemany('insert people values (%s, %s, %s)',
  4. ...          [ ('Sue', 'mus', '70000'),
  5. ...            ('Ann', 'mus', '60000')])
  6. 2L
  7. >>> conn.commit( )

>>> curs.execute('insert people values (%s, %s, %s)', ('Bob', 'dev', 5000))
1L
>>> curs.executemany('insert people values (%s, %s, %s)',
...          [ ('Sue', 'mus', '70000'),
...            ('Ann', 'mus', '60000')])
2L
>>> conn.commit( )

执行查询:

Python代码
  1. >>> curs.execute('select * from people')
  2. 6L
  3. >>> curs.fetchall( )
  4. (('Bob', 'dev', 5000L), ('Sue', 'mus', 70000L), ('Ann', 'mus', 60000L), ('Tom',
  5. 'mgr', 100000L))

>>> curs.execute('select * from people')
6L
>>> curs.fetchall( )
(('Bob', 'dev', 5000L), ('Sue', 'mus', 70000L), ('Ann', 'mus', 60000L), ('Tom',
'mgr', 100000L))

执行完数据库操作记得断开连接:

Python代码
  1. conn.close( )        # close, _ _del_ _ call rollback if changes not committed yet

conn.close( )        # close, _ _del_ _ call rollback if changes not committed yet

如果数据结构不是很复杂,配合Python强大的列表解析能力,不用ORM框架也是很方便的;或者自己封装对象映射也不是很难。

如果使用了Django框架,可以使用它自带的ORM工具来操作数据库。首先当然是编写实体类(或者叫模型)了:

Java代码
  1. from django.db import models
  2. class Musician(models.Model):
  3. first_name = models.CharField(max_length=50)
  4. last_name = models.CharField(max_length=50)
  5. instrument = models.CharField(max_length=100)
  6. class Album(models.Model):
  7. artist = models.ForeignKey(Musician)
  8. name = models.CharField(max_length=100)
  9. release_date = models.DateField()
  10. num_stars = models.IntegerField()

from django.db import modelsclass Musician(models.Model):first_name = models.CharField(max_length=50)last_name = models.CharField(max_length=50)instrument = models.CharField(max_length=100)class Album(models.Model):artist = models.ForeignKey(Musician)name = models.CharField(max_length=100)release_date = models.DateField()num_stars = models.IntegerField()

Python的代码已经很清楚了,类对应表,成员变量对应表的列,列属性由models.XXXField(...)定义。如果实体类没有显式定义主键,Django会默认加上一句:

Python代码
  1. id = models.AutoField(primary_key=True)

id = models.AutoField(primary_key=True)

Django里可以这样定义枚举型数据:

Python代码
  1. class Person(models.Model):
  2. GENDER_CHOICES = (
  3. (u'M', u'Male'),
  4. (u'F', u'Female'),
  5. )
  6. name = models.CharField(max_length=60)
  7. gender = models.CharField(max_length=2, choices=GENDER_CHOICES)

class Person(models.Model):GENDER_CHOICES = ((u'M', u'Male'),(u'F', u'Female'),)name = models.CharField(max_length=60)gender = models.CharField(max_length=2, choices=GENDER_CHOICES)

对于关联关系,在做列的映射定义时可以这么写:

Python代码
  1. poll = models.ForeignKey(Poll)
  2. sites = models.ManyToManyField(Site)
  3. place = models.OneToOneField(Place")

poll = models.ForeignKey(Poll)
sites = models.ManyToManyField(Site)
place = models.OneToOneField(Place")

在Django里定义关联关系还有更多功能,详细的还是看官方文档吧~

Django的Model基类中已经定义了基本的数据库操作,因为所有的实体类都是继承自Model类,所以也就有了这些操作。例如新建并保存一个person只需要这么做:

Python代码
  1. >>> p = Person(name="Fred Flinstone", gender="M")
  2. >>> p.save()

>>> p = Person(name="Fred Flinstone", gender="M")
>>> p.save()

Django会通过查询对象的主键是否存在来决定该UPDATE还是INSERT,当然你也可以强制框架执行某种操作。如果你不满意框架自带的方法,可以重写它:

Python代码
  1. class Blog(models.Model):
  2. name = models.CharField(max_length=100)
  3. tagline = models.TextField()
  4. def save(self, *args, **kwargs):
  5. do_something()
  6. super(Blog, self).save(*args, **kwargs) # Call the "real" save() method.
  7. do_something_else()

class Blog(models.Model):name = models.CharField(max_length=100)tagline = models.TextField()def save(self, *args, **kwargs):do_something()super(Blog, self).save(*args, **kwargs) # Call the "real" save() method.do_something_else()

发现没,Django里存取数据不需要那种session,最讨厌Hibernate里的session了,总是报“Session Closed”错误……

Python还有一个独立的ORM框架——SQLAlchemy。功能更强大,支持的数据库也比Django自带的ORM工具要多。它有两种建立实体类的方法。

一种是分开定义,再将表定义和类定义映射起来。首先是建立表的定义:

Python代码
  1. >>> from sqlalchemy import Table, Column, Integer, String, MetaData, ForeignKey
  2. >>> metadata = MetaData()
  3. >>> users_table = Table('users', metadata,
  4. ...     Column('id', Integer, Sequence('user_id_seq'), primary_key=True),
  5. ...     Column('name', String(50)),
  6. ...     Column('fullname', String(50)),
  7. ...     Column('password', String(12))
  8. ... )

>>> from sqlalchemy import Table, Column, Integer, String, MetaData, ForeignKey
>>> metadata = MetaData()
>>> users_table = Table('users', metadata,
...     Column('id', Integer, Sequence('user_id_seq'), primary_key=True),
...     Column('name', String(50)),
...     Column('fullname', String(50)),
...     Column('password', String(12))
... )

接着定义实体类:

Python代码
  1. >>> class User(object):
  2. ...     def __init__(self, name, fullname, password):
  3. ...         self.name = name
  4. ...         self.fullname = fullname
  5. ...         self.password = password

>>> class User(object):
...     def __init__(self, name, fullname, password):
...         self.name = name
...         self.fullname = fullname
...         self.password = password

这还没完,还要把他们映射起来:

Python代码
  1. >>> from sqlalchemy.orm import mapper
  2. >>> mapper(User, users_table)

>>> from sqlalchemy.orm import mapper
>>> mapper(User, users_table) 

这样的过程有点像Hibernate里将XML的Map文件和实体类的映射。Hibernate中还可以方便的直接用注释在实体类中完成与表的映射,当然SQLAlchemy也有直接的方法:

Python代码
  1. >>> from sqlalchemy.ext.declarative import declarative_base
  2. >>> Base = declarative_base()
  3. >>> class User(Base):
  4. ...     __tablename__ = 'users'
  5. ...
  6. ...     id = Column(Integer, primary_key=True)
  7. ...     name = Column(String)
  8. ...     fullname = Column(String)
  9. ...     password = Column(String)

>>> from sqlalchemy.ext.declarative import declarative_base>>> Base = declarative_base()
>>> class User(Base):
...     __tablename__ = 'users'
...
...     id = Column(Integer, primary_key=True)
...     name = Column(String)
...     fullname = Column(String)
...     password = Column(String)

作为一个独立的ORM框架,实体类的存取当然就不会像Django那样集成的那么完美了,SQLAlchemy里存取数据也是要Session的:

Python代码
  1. >>> from sqlalchemy.orm import sessionmaker
  2. >>> Session = sessionmaker(bind=engine)

>>> from sqlalchemy.orm import sessionmaker
>>> Session = sessionmaker(bind=engine)

这里的engine对象需要这样建立:

Python代码
  1. >>> from sqlalchemy import create_engine
  2. >>> engine = create_engine('<span style="font-family: monospace; white-space: normal; color: rgb(51, 51, 51); line-height: 20px;">dialect+driver://user:password@host/dbname[?key=value..]</span>', echo=True)

>>> from sqlalchemy import create_engine
>>> engine = create_engine('dialect+driver://user:password@host/dbname[?key=value..]', echo=True)

对于存取操作,如果是保存就这么写:

Python代码
  1. >>> ed_user = User('ed', 'Ed Jones', 'edspassword')
  2. >>> session.add(ed_user)

>>> ed_user = User('ed', 'Ed Jones', 'edspassword')
>>> session.add(ed_user)

如果要查询,就是类似的这种形式:

Python代码
  1. >>> our_user = session.query(User).filter_by(name='ed').first()

>>> our_user = session.query(User).filter_by(name='ed').first()

执行完一些数据操作,必要的时候要提交或是回滚:

Python代码
  1. >>> session.rollback()
  2. 或者
  3. >>> session.commit()

>>> session.rollback()
或者
>>> session.commit()

SQLAlchemy框架还有一个衍生产品——Elixir,在SQLAlchemy的基础上对其映射方式做了些封装,使得实体类的定义有点类似Django中的定义方式。

以上便是这两天对Python中数据存储的一些学习记录。话说Django的ORM与它的其他模块结合的很紧密,不好单独使用;SQLAlchemy虽 然强大,但风格不太喜欢,所以下一步打算深入两个ORM框架的代码,看看他们是怎么实现的。一方面好抉择用哪一个,另外也可以看看在自己的应用中能否自己 做一个简单的ORM。

转载于:https://blog.51cto.com/flandycheng/382280

简单比较Python的数据持久化操作相关推荐

  1. 独家 | 如何用简单的Python为数据科学家编写Web应用程序?(附代码链接)

    作者:拉胡尔·阿加瓦尔(Rahul Agarwal), Walmart 实验室的数据科学家 翻译:陈之炎 校对:闫晓雨 本文约4300字,建议阅读10分钟. 本文阐述如何使用StreamLit创建支持 ...

  2. 如何用简单的Python为数据科学家编写Web应用程序?(附代码链接)

    作者:拉胡尔·阿加瓦尔(Rahul Agarwal), Walmart 实验室的数据科学家 翻译:陈之炎  校对:闫晓雨 本文约4300字,建议阅读10分钟. 本文阐述如何使用StreamLit创建支 ...

  3. python存储数据的操作(csv格式文件,Excel表格文件)!!!

    python存储数据 存储数据的方式 两种存储数据方式的区别 csv格式文件 Excel格式文件 csv文件的写入 csv文件的读取 Excel基本概念 Excel文件的写入 Excel文件的读取 存 ...

  4. python获取系统时间函数_简单记录python的时间函数操作

    1. time和datetime模块 import datetime,time 2. 获得当前时间 time.time() #获得当前时间,返回float型 time.localtime([float ...

  5. 利用python进行数据可视化操作之描点连线(附python源码)

    作者:非妃是公主 专栏:<python学习> 个性签:顺境不惰,逆境不馁,以心制境,万事可成.--曾国藩 更具表格中的数据,画出相应的折线图: 时间 国民总收入(亿元) 1952 679. ...

  6. Python常见数据框操作①

    import numpy as np import pandas as pd from pandas import Sereis, DataFrame ser = Series(np.arange(3 ...

  7. python Dataframe数据相关操作

    1. 按条件筛选Excel中特定的数据(如只显示'result'列的值为'pass'或'fail'的数据) ex_df = pd.read_excel('./test',sheet_name = 'r ...

  8. 【redismemcached】数据类型、内存管理、数据持久化和集群管理的区别

    这几年redis很火,redis也常常被当做memcached的挑战者被提到桌面上来.关于redis和memcached的比较比比皆是.然而,redis真的在功能.性能以及内存使用效率上都超越memc ...

  9. IdentityServer4系列 | 支持数据持久化

    一.前言 在前面的篇章介绍中,一些基础配置如API资源.客户端资源等数据以及使用过程中发放的令牌等操作数据,我们都是通过将操作数据和配置数据存储在内存中进行实现的,而在实际开发生产中,我们需要考虑如何 ...

最新文章

  1. 计算机internet服务,计算机基础与应用——04Internet上的信息服务.ppt
  2. Android 10 中有关限制非 SDK 接口的更新
  3. f1 score 代码_2019JDATA-用户对品类下店铺的购买预测方案及代码分享(亚军)
  4. 如何设置并使用 Synology NAS 共享的多功能打印机
  5. CaffeMFC:caffe.pb.h(2525): error C2059: syntax error : 'constant'
  6. 声呐图像数据集_MaskedFace-Net 口罩人脸基准数据集,13万+图像数据
  7. 微信红包的算法实现探讨(基于PHP)
  8. 30行Python代码来绘制一个微信图标
  9. iText生成pdf详解
  10. ASP.NET- 执行SQL超时的解决方案
  11. linux修改ip配置文件路径,Centos7系统如何修改IP地址
  12. Mathematica颜色系,你喜欢哪一个?
  13. mysql lru scan depth_如何解决mysql警告:“ InnoDB:page_cleaner:1000毫秒的预期循环用了XXX毫秒。设置可能不是最佳的”?...
  14. ××项目日常工作制度和流程(草案)
  15. sql语句修改mysql数据库密码_修改mysql数据库密码的3中方法
  16. 防火墙阻止软件联网方法
  17. meltdown linux 补丁,宋宝华: ARM64 Linux meltdown修复补丁KPTI的最重要3个patch
  18. Java Web完整学习记录
  19. MPB:林科院袁志林组-野外树木根系取样及根际土收集操作规程
  20. 3.1 jmeter 响应断言

热门文章

  1. 会开了一天,赛题有结果了吗?
  2. 来自于参赛队伍所反映的总决赛落选之后的建议
  3. 几款高频环形磁芯的性能对比
  4. 利用MATLAB帮助求解作业中的Laplace变换和Z变换
  5. python与tableau结合_Python与Tableau相结合,万字长文搞定传统线下连锁店数据分析...
  6. 自我评价中专计算机600作文,自我评价作文600字
  7. 安卓java修改按钮大小_android弹出activity设置大小的方法
  8. mysql trim前后空格_MySQL清除字符串首尾空格函数trim
  9. 南昌职高计算机录取分数线,南昌运输职业技术学校2021年招生录取分数线
  10. csgo如何保存自己的cfg_KXCSGO:CSGO开箱饰品交易方法