我有一个 id
和 sort
的列表:
ids = ['123', '456', '789', '901'];
sorts = [1, 3, 2, 4];
我想更新 Django 中每个 id
的顺序。
这是我尝试过的 SQL 和 Django:
SQL:
UPDATE "Blogs"
SET sort = CASE
WHEN id = '123' THEN 1
WHEN id = '456' THEN 3
WHEN id = '789' THEN 2
WHEN id = '901' THEN 4
END
WHERE id IN (ids);
Django:
Blogs.objects.filter(
id=ids
).update(
sort=Case(
When(id=123, then=1),
When(id=456, then=3),
When(id=789, then=2),
When(id=901, then=4),
)
)
但问题是当 id 有很多元素时,我无法在 When(id={id}, then={sort}) 中指定
。
如何优化 Django 版本中的更新查询。
提前致谢。id
和 then
最佳答案
Django 没有明确提供您在这里需要的功能。您已经尝试过使用 CASE, WHEN
语法,随着 ID 数量的增加,它会变得难以管理。
我能想到的一个解决方案是创建一个只有 (id, sort)
列的临时表,然后加入该表以更新您的 Blog
表。
以下是您可以执行此操作的方法:
使用
id
和sort
列从Blog
表创建一个临时表:from django.db import connection cursor = connection.cursor() blog_tbl_name = Blog._meta.db_table temp_tbl_name = "tmp_{}".format(blog_tbl_name) sql = ( "CREATE TEMP TABLE {temp_tbl_name} AS " "SELECT id, sort FROM {blog_tbl_name} LIMIT 0;" .format( temp_tbl_name=temp_tbl_name, blog_tbl_name=blog_tbl_name ) ) cursor.execute(sql)
现在,将
(id, sort)
值插入到这个临时表中:ids = ['123', '456', '789', '901']; sorts = [1, 3, 2, 4]; insert_sql = ( "INSERT INTO {temp_tbl_name} (id, sort) VALUES (%s, %s);" .format(temp_tbl_name=temp_tbl_name) ) # zip these two together and insert cursor.executemany(insert_sql, zip(ids, sorts))
现在,最后一部分是通过在临时表中加入 id 来更新
Blog
表:update_sql = ( "UPDATE {blog_tbl_name} blog_tbl " "SET sort=tmp_tbl.sort " "FROM {temp_tbl_name} tmp_tbl " "WHERE blog_tbl.id = tmp_tbl.id;" .format( temp_tbl_name=temp_tbl_name, blog_tbl_name=blog_tbl_name ) ) cursor.execute(update_sql)
这里需要注意的是,整个过程只需要三个查询,并且易于管理且高效。
关于python - 在 Django 中更新条件,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43313938/