【发布时间】:2020-06-29 12:59:33
【问题描述】:
假设我有一个具有以下结构的数据库表
表格中有三列 - case id、dependent case id(s) 和 deployment status 的案例 ID。
我想使用下面编写的 SQL 查询查询从属案例 ID 列表中的案例 ID。
select distinct dep_case_id from tbl_name where case_id = 1
根据上面的例子,1 依赖于2。反过来2 依赖于3, 4, 5。并且,3 依赖于4,依此类推。我想遍历直到与案例 id 1 相关的链结束(即)dep_case_id 必须变为 0。
python sn-p(如下所示)正在构建列表列表。我的 SQL 查询只需要 1 个参数,并且列表列表不满足该条件。结果它失败了,下面提到的结果。
import pyodbc
cms_id_list = [1]
for i in cms_id_list:
cursor.execute('select distinct dep_cms_id from bfs_Test where cms_id = ?', i)
ids = cursor.fetchall()
print(ids)
first_tuple = [a_tuple[0] for a_tuple in ids]
cms_id_list.append(first_tuple)
print(cms_id_list)
输出
[(2, )] #first query result using case id 1...a tuple result
[1, [2]] #cms_id_list after 2 got appended to the list.
[(3, ), (4, )] #second query result using case id 2 (obtained in previous iteration...a tuple result)
[1, [2], [3, 4]] #cms_id_list after 3,4 got appended to the list.
Traceback (most recent call last):
File "C:\Users\Kris\eclipse-workspace\Utilities\Windows\recursion.py", line 22, in <module>
cursor.execute('select distinct dep_cms_id from bfs_Test where cms_id = ?', i)
pyodbc.ProgrammingError: ('The SQL contains 1 parameter markers, but 2 parameters were supplied', 'HY000')
预期的输出是cms_id_list = [1, 2, 3, 4, 5]。
我想要的只是将dep_case_ids 存储到一个扁平化的cms_id_list。我写的代码不起作用而且是错误的,因为会发生列表项重复。
我在某处读过 BFS 算法非常适合这种情况。我不知道如何实现它。这就是我实现这个基本代码 sn-p 的原因。
我愿意修改和改进代码。
【问题讨论】:
-
这与算法无关。代码有错误。 1)它将单个值和元组存储在一个容器中,这意味着您必须检查您正在阅读的内容。那很糟。 2)它在迭代时修改列表。您最终可能会两次读取相同的值,或者错过一个值。这也是非常低效的。 SQL 是一种面向集合的语言,它不需要循环。如果要检索分层数据,请使用 single 递归 CTE 检索从根一直到分支的所有行
-
BTW 递归 CTE 是大多数数据库中可用的标准 SQL 功能,包括 MySQL 8+
-
@PanagiotisKanavos 我已经根据您的建议回答了我自己的问题。谢谢你的建议:)
标签: python sql-server python-3.x tsql hierarchical-data