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模型类的更多相关文章

  1. python django -2 ORM模型

    ORM简介 MVC框架中包括一个重要的部分,就是ORM,它实现了数据模型与数据库的解耦,即数据模型的设计不需要依赖于特定的数据库,通过简单的配置就可以轻松更换数据库 ORM是“对象-关系-映射”的简称 ...

  2. ORM模型类介绍,

    所有的软件开发过程中,都会涉及到对象和关系型数据库,在用户层面和业务逻辑层面,程序员编写代码都是面向对象的,当我们对象的信息发生变化的时候,都需要将对应的信息,传到关系型数据库中.而在此之前,需要我们 ...

  3. laravel框架总结(八) -- ORM模型

    ORM模型简介 1>什么是ORM? ORM,即 Object-Relational Mapping(对象关系映射),它的作用是在关系型数据库和业务实体对象之间作一个映射,这样,我们在操作具体的 ...

  4. 利用Python实现一个感知机学习算法

    本文主要参考英文教材Python Machine Learning第二章.pdf文档下载链接: https://pan.baidu.com/s/1nuS07Qp 密码: gcb9. 本文主要内容包括利 ...

  5. python 面向对象进阶之元类metaclass

    一:知识储备 exec exec:三个参数 参数一:字符串形式的命令 参数二:全局作用域(字典形式),如果不指定,默认为globals() 参数三:局部作用域(字典形式),如果不指定,默认为local ...

  6. ORM模型简介

    ORM模型简介 1>什么是ORM? ORM,即 Object-Relational Mapping(对象关系映射),它的作用是在关系型数据库和业务实体对象之间作一个映射,这样,我们在操作具体的 ...

  7. 【Flask】ORM模型创建及数据库映射

    1. 用 declarative_base 根据 engine 创建一个ORM基类.2. 用 Base 类作为基类来写自己的ORM类.要定义 __tablename__ 类属性,来指定这个模型映射到数 ...

  8. laravel5.2总结--ORM模型

    ORM模型简介 1>什么是ORM? ORM,即 Object-Relational Mapping(对象关系映射),它的作用是在关系型数据库和业务实体对象之间作一个映射,这样,我们在操作具体的 ...

  9. SQLAlchemy01 /SQLAlchemy去连接数据库、ORM介绍、将ORM模型映射到数据库中

    SQLAlchemy01 /SQLAlchemy去连接数据库.ORM介绍.将ORM模型映射到数据库中 目录 SQLAlchemy01 /SQLAlchemy去连接数据库.ORM介绍.将ORM模型映射到 ...

随机推荐

  1. Maximum Value(CodeForces - 484B)

    Maximum Value Time limit 1000 ms Memory limit 262144 kB You are given a sequence a consisting of n i ...

  2. a链接刷新页面与js刷新页面总结

    1.a链接的使用操作: <a href="javascript:history.go(-1);">返回上一页</a> <a href="#t ...

  3. Python测试开发-浅谈如何自动化生成测试脚本

    Python测试开发-浅谈如何自动化生成测试脚本 原创: fin  测试开发社区  前天 阅读文本大概需要 6.66 分钟. 一 .接口列表展示,并选择 在右边,点击选择要关联的接口,区分是否要登录, ...

  4. JAVA学习大纲

    1.第一节 JAVA概念与JDK的安装 (1)JDK的安装和环境变量的设置: (2)相关基本概念:JDK.SDK.JRE.JVM.J2SE.J2EE.J2ME.java API.JAVA语言特点: ( ...

  5. 生死状:苹果VS他的供应商

    据知情人士透露,苹果已经组建了代号为Titan的汽车团队,并招募了数百名员工,准备进入汽车领域,iCar大有呼之欲出之势.事实上,苹果CEO蒂姆-库克早在去年就参观了宝马位于莱比锡的核心工厂,学习如何 ...

  6. Redis(2)——跳跃表

    一.跳跃表简介 跳跃表(skiplist)是一种随机化的数据结构,由 William Pugh 在论文<Skip lists: a probabilistic alternative to ba ...

  7. Java入门教程二(语言基础)

    常量与变量 常量值又称为字面常量,它是通过数据直接表示 常量 实型常量值 Java 的实型常量值主要有如下两种形式 十进制数形式:由数字和小数点组成,且必须有小数点,如 12.34.-98.0 科学记 ...

  8. Spring Cloud Feign 组成和配置

    Feign的组成 接口 作用 默认值 Feign.Builder Feign的入口 Feign.Builder Client Feign底层用什么去请求 和Ribbon配合时:LoadBalancer ...

  9. 聊一聊MyBatis 和 SQL 注入间的恩恩怨怨

    整理了一些Java方面的架构.面试资料(微服务.集群.分布式.中间件等),有需要的小伙伴可以关注公众号[程序员内点事],无套路自行领取 更多优选 一口气说出 9种 分布式ID生成方式,面试官有点懵了 ...

  10. 如何优雅地删除 Linux 中的垃圾文件

    不知道大家是否也跟我一样,是一只要把的自己电脑文件安排的条理有序,把没用的文件会及时删掉的程序猿呢?如果是的话,那么我们可以愉快地探讨下文章的内容.如果不是的话,你也可以留下来凑凑热闹嘛(>-& ...