使用 CASE 和 IN 进行更新 - Oracle
我编写了一个查询,它在 SQL Server 中就像一个魅力一样。不幸的是它需要在 Oracle 数据库上运行。我一直在网上彻底搜索如何转换它的解决方案,但没有成功:/
查询看起来像这样 i SQL:
UPDATE tab1 SET budgpost_gr1=
CASE WHEN (budgpost in (1001,1012,50055)) THEN 'BP_GR_A'
WHEN (budgpost in (5,10,98,0)) THEN 'BP_GR_B'
WHEN (budgpost in (11,876,7976,67465))
ELSE 'Missing' END`
我的问题还在于列 budgetpost_gr1
和 Budgetpost 是字母数字和Oracle 似乎希望将列表视为数字。该列表是预定义为逗号分隔列表的变量/参数,仅转储到查询中。
I wrote a query that works like a charm in SQL Server. Unfortunately it needs to be run on an Oracle db. I have been searching the web inside out for a solution on how to convert it, without any success :/
The query looks like this i SQL:
UPDATE tab1 SET budgpost_gr1=
CASE WHEN (budgpost in (1001,1012,50055)) THEN 'BP_GR_A'
WHEN (budgpost in (5,10,98,0)) THEN 'BP_GR_B'
WHEN (budgpost in (11,876,7976,67465))
ELSE 'Missing' END`
My problem is also that the columns budgetpost_gr1
and budgetpost is alphanumeric and Oracle seems to want to see the list as numbers. The list are variables/parameters that is pre-defined as comma separated lists, which is just dumped into the query.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(5)
你说预算帖子是字母数字的。这意味着它正在寻找与字符串的比较。您应该尝试将参数括在单引号中(并且您缺少 Case 表达式中的最后一个 THEN)。
You said that budgetpost is alphanumeric. That means it is looking for comparisons against strings. You should try enclosing your parameters in single quotes (and you are missing the final THEN in the Case expression).
使用
to_number
将budgpost
转换为数字:编辑:确保
to_number
中有足够的9
与最大的预算职位相匹配。如果存在非数字预算帖子,您可以在查询末尾使用
where
子句将其过滤掉:Use
to_number
to convertbudgpost
to a number:EDIT: Make sure there are enough
9
's into_number
to match to largest budget post.If there are non-numeric budget posts, you could filter them out with a
where
clause at then end of the query:得到了一个可以运行的解决方案。但不知道这是否是最佳的。我所做的是根据 http://blogs.oracle.com 拆分字符串/aramamoo/2010/05/how_to_split_comma_separated_string_and_pass_to_in_clause_of_select_statement.html
使用:
从对偶中选择 regexp_substr(' 1, 2 , 3 ','[^,]+', 1, level)
connect by regexp_substr('1 , 2 , 3 ', '[^,]+', 1, level) is not null;
所以我的最终代码如下所示 (
$bp_gr1'
是像1,2,3
这样的字符串):有没有办法让它运行得更快?
Got a solution that runs. Don't know if it is optimal though. What I do is to split the string according to http://blogs.oracle.com/aramamoo/2010/05/how_to_split_comma_separated_string_and_pass_to_in_clause_of_select_statement.html
Using:
select regexp_substr(' 1, 2 , 3 ','[^,]+', 1, level) from dual
connect by regexp_substr('1 , 2 , 3 ', '[^,]+', 1, level) is not null;
So my final code looks like this (
$bp_gr1'
are strings like1,2,3
):Is there a way to make it run faster?
“该列表是预定义为逗号分隔列表的变量/参数”。
您的意思是您的查询实际上是
如果是的话,您需要一个函数来获取字符串并将其解析为数字列表。
然后你可以像这样使用该函数:
"The list are variables/paramaters that is pre-defined as comma separated lists".
Do you mean that your query is actually
If so, you need a function to take a string and parse it into a list of numbers.
Then you can use the function like so:
您可以使用另一种解决方法来使用联接进行更新。下面的示例假设您希望通过包含查找值(在本例中在表中存储用户名)来对表进行反规范化。更新包括查找名称的联接,并在支持找到或未找到名称的 CASE 语句中评估输出。完成这项工作的关键是确保来自连接的所有列都具有唯一的名称。在示例代码中,请注意 b.user_name 如何与 a.user_name 列冲突,并且必须使用唯一名称“user_user_name”作为别名。
There is another workaround you can use to update using a join. This example below assumes you want to de-normalize a table by including a lookup value (in this case storing a users name in the table). The update includes a join to find the name and the output is evaluated in a CASE statement that supports the name being found or not found. The key to making this work is ensuring all the columns coming out of the join have unique names. In the sample code, notice how b.user_name conflicts with the a.user_name column and must be aliased with the unique name "user_user_name".