Python实现一个ORM模型类
ORM是三个单词首字母组合而成,包含了Object(对象-类),Relations(关系),Mapping(映射)。解释过字面意思,但ORM的概念仍然模糊。私以为要理解一个事物,最好的法子是搞明白它出现是为了解决什么问题。
一个简单的ORM模型
我们也可以通过元类来实现自己的ORM。下面将涉及两个知识点:元类,描述符。
首先完成属性描述符的设计:
class BaseFiled(object):
pass class CharFiled(BaseFiled):
def __init__(self, max_len=10):
self.max_len = max_len def __get__(self, instance, owner):
return self.value def __set__(self, instance, value):
if isinstance(value, str):
# 判断类型进行控制
if len(value) <= self.max_len:
self.value = value
else:
raise TypeError('超出最大长度')
else:
raise TypeError('need a str') def __delete__(self, instance):
self.value = None class IntFiled(BaseFiled):
def __init__(self, max_len=10):
self.max_len = max_len def __get__(self, instance, owner):
return self.value def __set__(self, instance, value):
if isinstance(value, int):
# 判断类型进行控制
if len(str(value)) <= self.max_len:
self.value = value
else:
raise TypeError('超出最大长度')
else:
raise TypeError('need a int') def __delete__(self, instance):
self.value = None class BoolFiled(BaseFiled):
def __init__(self, max_len=10):
self.max_len = max_len def __get__(self, instance, owner):
return self.value def __set__(self, instance, value):
if isinstance(value, bool):
# 判断类型进行控制
self.value = value
else:
raise TypeError('need a bool')
实现一个元类:
class FieldMetaClass(type):
# 创建模型类的元类
def __new__(cls, name, bases, dic, *args, **kwargs):
if name == 'BaseModel':
return super().__new__(cls, name, bases, dic)
table_name = name.lower()
# 将类名转换成小写,对应数据表的名称
fields = {}
for k, v in dic.items():
# 判断value的类型是不是BaseFiled类型的 因为调用的类的父类就是BaseFiled 所以通过CharFiled等创建出来的对象也就是BaseFiled类型的
if isinstance(v, BaseFiled):
fields[k] = v
dic['t_name'] = table_name
dic['fields'] = fields
# 将类名和属性取出来放在一个字典中
return super().__new__(cls, name, bases, dic)
给模型类创建一个父类,具体原因及作用可以观察注释:
class BaseModel(metaclass=FieldMetaClass):
# 模型类的父类
def __init__(self, **kwargs):
# kwargs 传入的是一个字典
for k, v in kwargs.items():
setattr(self, k, v)
# setattr 设置属性 传入对象、属性名、属性值 def save(self):
# 保存一条数据,生成一条对应的sql语句
# 获取表名
t_name = self.t_name
# 获取字段名称
fields = self.fields
# 获取对应字段的值
filed_dict = {} # 创建一个字典用来存储键值对
for filed in fields.keys():
value = getattr(self, filed)
# 把遍历出来的键中的值找到
filed_dict[filed] = value # 生成对应的sql语句
sql = 'INSERT INTO {0} VALUES {1};'.format(t_name, tuple(filed_dict.values()))
生成模型类:
class User(BaseModel):
# 用户模型类 在模型类中不会重写init方法,在它的父类中写init方法 它会自动继承
username = CharFiled()
pwd = CharFiled()
age = IntFiled()
live = BoolFiled()
调用方式:
a = User(username='', pwd='', age=20, live=True)
a.save()
这样就实现了一个模型类,注释写的个人感觉还是比较清晰的,有不清楚的欢迎留言交流
Python实现一个ORM模型类的更多相关文章
- python django -2 ORM模型
ORM简介 MVC框架中包括一个重要的部分,就是ORM,它实现了数据模型与数据库的解耦,即数据模型的设计不需要依赖于特定的数据库,通过简单的配置就可以轻松更换数据库 ORM是“对象-关系-映射”的简称 ...
- ORM模型类介绍,
所有的软件开发过程中,都会涉及到对象和关系型数据库,在用户层面和业务逻辑层面,程序员编写代码都是面向对象的,当我们对象的信息发生变化的时候,都需要将对应的信息,传到关系型数据库中.而在此之前,需要我们 ...
- laravel框架总结(八) -- ORM模型
ORM模型简介 1>什么是ORM? ORM,即 Object-Relational Mapping(对象关系映射),它的作用是在关系型数据库和业务实体对象之间作一个映射,这样,我们在操作具体的 ...
- 利用Python实现一个感知机学习算法
本文主要参考英文教材Python Machine Learning第二章.pdf文档下载链接: https://pan.baidu.com/s/1nuS07Qp 密码: gcb9. 本文主要内容包括利 ...
- python 面向对象进阶之元类metaclass
一:知识储备 exec exec:三个参数 参数一:字符串形式的命令 参数二:全局作用域(字典形式),如果不指定,默认为globals() 参数三:局部作用域(字典形式),如果不指定,默认为local ...
- ORM模型简介
ORM模型简介 1>什么是ORM? ORM,即 Object-Relational Mapping(对象关系映射),它的作用是在关系型数据库和业务实体对象之间作一个映射,这样,我们在操作具体的 ...
- 【Flask】ORM模型创建及数据库映射
1. 用 declarative_base 根据 engine 创建一个ORM基类.2. 用 Base 类作为基类来写自己的ORM类.要定义 __tablename__ 类属性,来指定这个模型映射到数 ...
- laravel5.2总结--ORM模型
ORM模型简介 1>什么是ORM? ORM,即 Object-Relational Mapping(对象关系映射),它的作用是在关系型数据库和业务实体对象之间作一个映射,这样,我们在操作具体的 ...
- SQLAlchemy01 /SQLAlchemy去连接数据库、ORM介绍、将ORM模型映射到数据库中
SQLAlchemy01 /SQLAlchemy去连接数据库.ORM介绍.将ORM模型映射到数据库中 目录 SQLAlchemy01 /SQLAlchemy去连接数据库.ORM介绍.将ORM模型映射到 ...
随机推荐
- zookeeper 客户端连接报: Will not attempt to authenticate using SASL
解决方法:我在学习zk的时候,用客户端连接zk,发现接收不到watch通知,并且报 如图所示错误: 后查看服务没问题:图示 后查看防火墙状态,关闭防火墙 连接后正常: 如果查看防火墙状态是dead,s ...
- SpringMVC之reset风格和form表单格式的curd
CRUD c:create创建 r:retieve:查询 u:update:修改 d:delete:删除 rest /emp/1 get 代表查询id为1的员工 /emp/1 put 代表修改id为1 ...
- linux vi命令详解及使用技巧
进入vi的命令vi filename :打开或新建文档,并将光标置于第一行首vi +n filename :打开文档,并将光标置于第n行首vi + filename :打开文档,并将光标置于最后一行首 ...
- 来自澳洲的数据秀场:记KDD 2015大会
作者:微软亚洲研究院实习生 王英子 南半球最大城市和数据挖掘界顶级会议的浪漫碰撞 悉尼,作为澳大利亚第一大城市及新南威尔士州首府,澳大利亚的经济.金融.航运和旅游中心,同时还是南半球最大的城市和重要的 ...
- fastcgi_param详解
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;#脚本文件请求的路径 fastcgi_param QUERY_STRI ...
- Git的安装与TortoiseGit的安装和汉化
下载Git 进入https://git-scm.com/downloads 可以看到如下界面 因为我是windows系统,选择windows即可. 有的朋友因为网络慢的一些原因不能很快下载下来,可以进 ...
- MySQL多表查询、事务、DCL:内含mysql如果忘记密码解决方案
MySQL多表查询.事务.DCL 多表查询 * 查询语法: select 列名列表 from 表名列表 where.... * 准备sql # 创建部门表 CREATE TABLE dept( id ...
- 自然语言处理NLTK之入门
环境:window10 + python3 一.安装NLTK pip install nltk # 或者 PyCharm --> File --> Settings --> Proj ...
- JSR310-新日期APIJSR310新日期API(完结篇)-生产实战
前提 前面通过五篇文章基本介绍完JSR-310常用的日期时间API以及一些工具类,这篇博文主要说说笔者在生产实战中使用JSR-310日期时间API的一些经验. 系列文章: JSR310新日期API(一 ...
- JZOJ 5286. 【NOIP2017提高A组模拟8.16】花花的森林 (Standard IO)
5286. [NOIP2017提高A组模拟8.16]花花的森林 (Standard IO) Time Limits: 1000 ms Memory Limits: 131072 KB Descript ...