您好我有一个分区表,当我尝试更新在循环中使用动态传递分区名称的少数选定分区时,它不起作用。
for i in 1..partition_tbl.count Loop
UPDATE cdr_data PARTITION(partition_tbl(i)) cdt
SET A='B'
WHERE
cdt.ab='c'
End Loop;
partition_tbl对象具有我要在其中执行此更新的所有分区。
请建议我如何继续这里。
提前致谢
答案 0 :(得分:3)
您要解决的问题是什么?对循环中的每个分区运行单独的UPDATE
语句没有意义。如果您确实要更新表ab = 'c'
中的每一行,只需发出一个UPDATE
语句
UPDATE cdr_data cdt
SET a = 'B'
WHERE ab = 'c'
可能带有PARALLEL
提示,允许Oracle并行更新多个分区。
如果你确实想要独立更新每个分区,那么基于分区键这样做会更有意义。例如,如果您的表具有基于日期的每日分区
FOR i IN 1 .. <<number of daily partitions>>
LOOP
UPDATE cdr_data cdt
SET a = 'B'
WHERE ab = 'c'
AND partition_key = <<minimum date>> + i;
END LOOP;
使用partition( <<partition name>> )
语法是绝对的最后手段。如果您真的决定沿着这条路走下去,那么您需要使用动态SQL,在循环中构造SQL语句并使用EXECUTE IMMEDIATE
或dbms_sql
来执行它。
答案 1 :(得分:2)
最好让Oracle关注分区 - 在你的陈述中假装它们不存在
UPDATE cdr_data cdt SET A='B' WHERE cdt.ab='c'
它将从where条件和您的分区定义中选择要应用命令的正确分区。
当您需要分区绑定DML时,可能会发生罕见事件,但肯定不是显示的示例。在这种情况下,您无法动态提供分区名称,就像您通常无法动态提供分区名称一样。你不能
select * from _variable_containing_table_name
如果你真的坚持分区有界命令,那么它将是
select * from table_name partition (partition_Name)
e.g。
select * from bills partition (p201403)
要使用动态分区名称,必须通过execute immediate或dbms_sql动态执行整个语句。
但是再一次,不要选择分区,Oracle会。