【问题标题】:How can i Swap two values我如何交换两个值
【发布时间】:2017-08-22 19:15:54
【问题描述】:

我有以下数据。

TRACK_ID      CT_ID           IMAGE_SORT_NO       IMAGE_LEVEL
132071        63461               1                image_1
132081        63461               2                image_2
132091        63461               3                image_3

Image_sort_no 是主键。每个 image_sort_no 都有一张图片。我必须交换 1 到 3 和 3 到 1 的值。我的预期输出看起来像

TRACK_ID      CT_ID           IMAGE_SORT_NO       IMAGE_LEVEL
132071        63461               1                image_3
132081        63461               2                image_2
132091        63461               3                image_1

如果我运行以下更新语句,则会丢失 1 的 image_level。

Update cd_offender
   set image_level = image_3
 Where IMAGE_SORT_NO = 1;

如何在不丢失任何内容的情况下交换值?

【问题讨论】:

  • 我不想做硬编码。简单来说,我必须将第一个值与最后一个值交换。
  • 如果每个 ct_id 有 4 条或 5 条或更多条记录呢?只是第一个和最后一个被交换?
  • 可以,只需要先和后交换即可。
  • 那么,image_sort_no 不仅是 1-3,还可以有更多?在 first 和 last 之间,image_level 不会改变?

标签: sql oracle sql-update


【解决方案1】:

试试:

With xxx As (
  SELECT *
  FROM (
    SELECT IMAGE_SORT_NO As min_sort_no, 
           IMAGE_LEVEL As min_IMAGE_LEVEL
    FROM cd_offender
    ORDER BY IMAGE_SORT_NO LIMIT 1
  ) x
  CROSS JOIN (
    SELECT IMAGE_SORT_NO As max_sort_no, 
           IMAGE_LEVEL As max_IMAGE_LEVEL
    FROM cd_offender
    ORDER BY IMAGE_SORT_NO DESC LIMIT 1
  ) y
)
UPDATE cd_offender t
SET IMAGE_LEVEL = CASE
    WHEN IMAGE_SORT_NO = xxx.min_sort_no THEN xxx.max_image_level
    WHEN IMAGE_SORT_NO = xxx.max_sort_no THEN xxx.min_image_level
    ELSE IMAGE_LEVEL -- just to be on the safe side
END
FROM xxx
WHERE IMAGE_SORT_NO IN (xxx.min_sort_no, xxx.max_sort_no )
;

演示:http://sqlfiddle.com/#!17/8e19d/6

【讨论】:

    【解决方案2】:

    这将只在第一个和最后一个值之间交换 image_level 的值

    SELECT t1.track_id,
           t1.ct_id,
           t1.image_sort_no,
           CASE WHEN t1.image_sort_no = t2.firstsort THEN t2.firstvalue
                WHEN t1.image_sort_no = t2.lastsort THEN t2.lastvalue
                ELSE t1.image_level
            END image_level
      FROM cd_offender t1
      LEFT OUTER JOIN (SELECT ct_id,       
                              MAX(image_sort_no) KEEP (DENSE_RANK FIRST ORDER BY image_sort_no) firstsort,
                              MAX(image_level) KEEP (DENSE_RANK LAST ORDER BY image_sort_no) firstvalue,
                              MAX(image_sort_no) KEEP (DENSE_RANK LAST ORDER BY image_sort_no) lastsort,
                              MAX(image_level) KEEP (DENSE_RANK FIRST ORDER BY image_sort_no) lastvalue
                         FROM cd_offender
                        GROUP BY ct_id) t2
        ON t1.ct_id = t2.ct_id
     ORDER BY t1.ct_id,
              t1.track_id,       
              t1.image_sort_no;
    

    更新

    MERGE INTO cd_offender 
    USING 
    (
      SELECT t1.track_id,
           t1.ct_id,
           t1.image_sort_no,
           CASE WHEN t1.image_sort_no = t2.firstsort THEN t2.firstvalue
                WHEN t1.image_sort_no = t2.lastsort THEN t2.lastvalue
                ELSE t1.image_level
            END image_level
      FROM cd_offender t1
      LEFT OUTER JOIN (SELECT ct_id,       
                              MAX(image_sort_no) KEEP (DENSE_RANK FIRST ORDER BY image_sort_no) firstsort,
                              MAX(image_level) KEEP (DENSE_RANK LAST ORDER BY image_sort_no) firstvalue,
                              MAX(image_sort_no) KEEP (DENSE_RANK LAST ORDER BY image_sort_no) lastsort,
                              MAX(image_level) KEEP (DENSE_RANK FIRST ORDER BY image_sort_no) lastvalue
                         FROM cd_offender
                        GROUP BY ct_id) t2
        ON t1.ct_id = t2.ct_id
     ORDER BY t1.ct_id,
              t1.track_id,       
              t1.image_sort_no
    ) ta  ON (ta.track_id = t_image.track_id
         AND ta.ct_id = t_image.ct_id
         AND ta.image_sort_no = t_image.image_sort_no)
      WHEN MATCHED THEN UPDATE 
       SET t_image.image_level = ta.image_level;
    

    【讨论】:

    • 是的,这个查询正在工作。但是如何使用此查询更新我的表?
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-07-20
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多