Sqlalchemy join连表查询

2023-11-06

摘要1:https://blog.csdn.net/weixin_33804582/article/details/92471702
摘要2:https://www.cnblogs.com/juandx/p/5442752.html
摘要3:https://www.cnblogs.com/wuheng-123/p/9719812.html

model存在外键做join连接

首先创建数据库,在这里一个user对应多个address,因此需要在address上增加user_id这个外键(一对多)。


from sqlalchemy import create_engine
from sqlalchemy import Column
from sqlalchemy import Integer
from sqlalchemy import String
from sqlalchemy import ForeignKey
from sqlalchemy.orm import backref
from sqlalchemy.orm import sessionmaker
from sqlalchemy.orm import relationship, backref
from sqlalchemy.ext.declarative import declarative_base
 
Base = declarative_base()
 
 
class User(Base):
    __tablename__ = 'users'
 
    id = Column(Integer, primary_key=True)
    name = Column(String(32))

    addresses = relationship("Address", order_by="Address.id", backref="user")
 
class Address(Base):
    __tablename__ = 'addresses'
    id = Column(Integer, primary_key=True)
    email_address = Column(String(32), nullable=False)
    user_id = Column(Integer, ForeignKey('users.id'))
 
    #user = relationship("User", backref=backref('addresses', order_by=id))
 
engine  = create_engine('mysql://root:root@localhost:3306/test', echo=True)
#Base.metadata.create_all(engine)

1.如果不使用join的话,可以直接联表查询

>>> session.query(User.name, Address.email_address).filter(User.id==Address.user_id).filter(Address.email_address=='test@test.com').all()
2015-08-19 14:02:02,877 INFO sqlalchemy.engine.base.Engine SELECT users.name AS users_name, addresses.email_address AS addresses_email_address 
FROM users, addresses 
WHERE users.id = addresses.user_id AND addresses.email_address = %s
2015-08-19 14:02:02,878 INFO sqlalchemy.engine.base.Engine ('test@test.com',)
[('jack', 'test@test.com')]

2.使用sqlalchemy中提供了Queqy.join()函数

>>> session.query(User).join(Address).filter(Address.email_address=='test@test.com').first()
2015-08-19 14:06:56,624 INFO sqlalchemy.engine.base.Engine SELECT users.id AS users_id, users.name AS users_name 
FROM users INNER JOIN addresses ON users.id = addresses.user_id 
WHERE addresses.email_address = %s 
 LIMIT %s
2015-08-19 14:06:56,624 INFO sqlalchemy.engine.base.Engine ('test@test.com', 1)
<demo.User object at 0x7f9a74139a10>

model不存在外键做join连接

1.上面的用法的前提是存在外键的情况下,如果没有外键,如何做join连接

from sqlalchemy import create_engine
from sqlalchemy import Column
from sqlalchemy import Integer
from sqlalchemy import String
from sqlalchemy import ForeignKey
from sqlalchemy.orm import backref
from sqlalchemy.orm import sessionmaker
from sqlalchemy.orm import relationship, backref
from sqlalchemy.ext.declarative import declarative_base
 
Base = declarative_base()
 
class User(Base):
    __tablename__ = 'users'
 
    id = Column(Integer, primary_key=True)
    name = Column(String(32)) 
 
class Address(Base):
    __tablename__ = 'addresses'
    id = Column(Integer, primary_key=True)
    email_address = Column(String(32), nullable=False)
    user_id = Column(Integer, ForeignKey('users.id'))
 
    #user = relationship("User", backref=backref('addresses', order_by=id))
 
engine  = create_engine('mysql://root:root@localhost:3306/test', echo=True)
#Base.metadata.create_all(engine)
# 上面model对应示例
query.join(Address, User.id==Address.user_id)


# 其他sql示例
result = session.query(User.username,func.count(Article.id)).join(Article,User.id==Article.uid).\
    group_by(User.id).order_by(func.count(Article.id).desc()).all()
print(result)#[('ketang', 2), ('zhiliao', 1)]

'''
SELECT user.username AS user_username, count(article.id) AS count_1 
FROM user INNER JOIN article ON user.id = article.uid GROUP BY user.id ORDER BY count(article.id)
'''

子查询示例

# 原生sql,子表查询
mysql> SELECT users.*, adr_count.address_count FROM users LEFT OUTER JOIN
    ->     (SELECT user_id, count(*) AS address_count
    ->         FROM addresses GROUP BY user_id) AS adr_count
    ->     ON users.id=adr_count.user_id;
+----+------+---------------+
| id | name | address_count |
+----+------+---------------+
|  1 | jack |             2 |
+----+------+---------------+
1 row in set (0.00 sec)

使用sqlalchemy子查询


# 生成子句,等同于(select user_id ... group_by user_id)
>>> sbq = session.query(Address.user_id, func.count('*').label('address_count')).group_by(Address.user_id).subquery()
 
# 联接子句,注意子句中需要使用c来调用字段内容
>>> session.query(User.name, sbq.c.address_count).outerjoin(sbq, User.id==sbq.c.user_id).all()
2015-08-19 14:42:53,425 INFO sqlalchemy.engine.base.Engine SELECT users.name AS users_name, anon_1.address_count AS anon_1_address_count
FROM users LEFT OUTER JOIN (SELECT addresses.user_id AS user_id, count(%s) AS address_count
FROM addresses GROUP BY addresses.user_id) AS anon_1 ON users.id = anon_1.user_id
2015-08-19 14:42:53,425 INFO sqlalchemy.engine.base.Engine ('*',)
[('jack', 2L)]
>>>
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Sqlalchemy join连表查询 的相关文章

随机推荐

  • 基于OpenVINO部署PaddlePadle-YOLOE模型—4.Python实现

    1 环境安装 OpenVINOTM工具套件2022 1版于2022年3月22日正式发布 与以往版本相比发生了重大革新 提供预处理API函数 ONNX前端API AUTO 设备插件 并且支持直接读入飞桨模型 在推理中中支持动态改变模型的形状
  • react好租客项目Day07-条件筛选功能实现&FilterTitle组件功能实现&房屋列表数据获取

    列表找房模块 条件筛选 目标 能够设置FilterPicker组件为受控组件 能够获取选中值 并且设置默认选中值 获取选中值 在FilterPicker组件中 添加状态value 用于获取PickerView组件的选中值 state val
  • Jina 实例秀 —— 智能聊天机器人

    Jina将开启一个全新的教程系列 实例秀 在这个系列中我们将进行Jina实际用例的教学 手把手教你把Jina用起来 在本教程中 你将创建一个基于文本到文本模型的聊天机器人 了解这个示例的每个部分是如何工作的 以及如何使用不同数据集来创建自己
  • 树莓派4B安装ROS的方法总结

    文章目录 准备 Raspberry Pi 安装ROS Ubuntu Mate安装ROS Ubuntu Server安装ROS Ubuntu Desktop安装ROS 总结 故障问题解决 sudo rosdep init rosdep upd
  • 配置acados时出现“Segmentation fault,Exception: Rendering of main.in.c failed!”报错

    问题描述 在安装acados后运行测试节点时出现错误 liangjunming XX program acados examples acados python getting started on git master o 11 49 1
  • 如何安装Chrome OS系统

    Chrome OS是由Google设计的基于Linux内核的操作系统 它源自免费软件Chromium OS 并使用Google Chrome网络浏览器作为其主要用户界面 因此 Chrome操作系统主要支持Web应用程序 谷歌于2009年7月
  • 【Linux】Shell脚本中获取命令运行的结果

    前言 写shell脚本的时候 常需要将一个命令的运行结果做为参数传递给另外一个命令 除了我们熟知的管道 和args 我们也可以通过获取命令的运行结果 1 通过反引号 command 来完成 result date echo result r
  • 象牙塔式的开发

    我向来不鼓励象牙塔式的开发模式 开发团队常年封闭在 高塔 之中 一门心思地做着魔法一样的软件 这些开发者根本不知道用户会怎样使用他们做出来的软件 你若问他们 最近一次面见用户是在什么时候 他们甚至可能都回答不上来 因为缺失强有力的证据 开发
  • HOOK框架——静态代理

    往期推荐 实战案列分析 Crakeme01 实战 AliCrackme 实战案列 AntiDebug self debugging反调试 需要相关资料的朋友 可以 加入此处即可打包获取 代理模式分为静态代理和动态代理 静态代理是编译阶段就生
  • C++学习日记1

    1 头文件 输入输出流 include
  • nanomsg(3): push/pull 模式

    推拉之间构建起数据的双向交互 值得注意的是 先推再拉 和先拉再推 并没有启动的先后顺序 pull cpp include
  • Linux搭建部署JDK1.7环境

    jdk下载 官网链接 https www oracle com java technologies javase javase7 archive downloads html jdk 7u80 oth JPR 打开linux系统的终端 在l
  • python题目58:工厂流水线调度

    一个工厂有m条流水线 来并行完成n个独立的作业 该工厂设置了一个调度系统 在安排作业时 总是优先执行处理时间最短的作业 现给定流水线个数m 需要完成的作业数n 每个作业的处理时间分别为 t1 t2 tn 请你编程计算处理完所有作业的耗时为多
  • Docker+NETCore系列文章(四、镜像commit操作)

    文章目录 镜像commit操作 一 Docker安装Tomcat 二 镜像commit操作 1 命令解析 2 实操 赞赏 镜像commit操作 一 Docker安装Tomcat 1 官方使用方法 用完容器就删除 docker run it
  • AD画PCB板子 基本步骤

    软件环境 Altium Designer13 汉化版 plus 大二上的电子工艺实习 第一次画pcb板子 在大佬的耐心指导下 反复倒腾这个软件 把步骤整理下 help其它新手 一 画原理图步骤 Schdoc文件 1 新建工程 点击左上角 2
  • Kettle入门(六)

    资源库 数据库资源库 数据库资源库是将作业和转换相关的信息存储在数据库中 执行的时候直接去数据库读取信息 便于跨平台使用 操作步骤 1 点击右上角 connect 选择 Other Resporitory 2 选择 Database Rep
  • dom影像图形成数字地形图_基于MapMatrix的数字正射影像图制作

    施卫东 周小扬 摘 要本论文基于武汉航天远景科技股份有限公司的新型数字摄影测量系统MapMatrix 结合武汉商学院三维数字校园生产实践进行1 2000数字正射影像图制作 探讨数字正射影像图 DOM 的制作方法 并说明了MapMatrix相
  • 关于md文件插入视频链接的方法。(亲测可用)

    md文件中插入了HTML5的代码 如下
  • 【计算机基础知识9】前端设计模式与常见类型

    目录 一 前言 二 设计模式的基本概念和原则 三 创建型设计模式 四 结构型设计模式 五 行为型设计模式 六 MVC和MVVM框架中的设计模式 七 实际应用案例分析 一 前言 在软件开发领域 设计模式是一种解决常见问题的最佳实践 它可以帮助
  • Sqlalchemy join连表查询

    摘要1 https blog csdn net weixin 33804582 article details 92471702 摘要2 https www cnblogs com juandx p 5442752 html 摘要3 htt