1

と呼ばれるテーブルがPRODUCTSあり、それぞれPRODUCT_NO_REGISTRATION_NOが製品の開始日と返品日が衝突しないように1回だけ使用できます。

商品を返品し、返品日を入力します。nullACTUAL_RETURN_DATEの場合は返品日とします。ACTUAL_RETURN_DATEEND_DATE

ここでレコードを見ることができます

例えばPRODUCT_NO_REGISTRATION_NO is clashing, as HP_2014 is returned on 18-Jun-2001, however HP_2012 same PRODUCT_NO_REGISTRATION_NO is allotted on 18-Jun-2001.

レコードが重複しているかどうかをSQLを使用して確認するにはどうすればよいですか?

アップデート1

PRODUCTSを含めるためにテーブルに変更がありましたPRODUCT_EXTENSION_NO。の組み合わせはPRODUCT_NO,PRODUCT_NO_REGISTRATION_NO and PRODUCT_EXTENSION_NO一意の行(複合主キー)になります。

ルールは以下のとおりPRODUCT_NO_REGISTRATION_NOです。製品の開始日と返品日が競合しないように、それぞれを1回だけ使用できます。

商品を返品し、返品日を入力します。nullACTUAL_RETURN_DATEの場合は返品日とします。ACTUAL_RETURN_DATEEND_DATE

PRODUCT_NO拡張機能があるため、END_DATEが拡張されます。

SQLフィドル

たとえば、レコード PRODUCT_NO--with--ORP76PRODUCT_EXTENSION_NO--with--1と衝突しているPRODUCT_NO場合。ORP100PRODUCT_EXTENSION_NO0

レコードが重複しているかどうかをSQLを使用して確認するにはどうすればよいですか?ただし、の拡張PRODUCT_NOは許可されています。つまりPRODUCT_NO ORP76、拡張機能0と拡張機能1は基本的に拡張されます。

4

1 に答える 1

1

それが一意であると仮定すると、product_no製品テーブルに自己結合して、重複する日付を確認できます。

select *
  from PRODUCTS
 inner join products products_test
    on products.PRODUCT_NO_REGISTRATION_NO 
     = products_test.PRODUCT_NO_REGISTRATION_NO
   and products.start_date 
    <= nvl (products_test.ACTUAL_RETURN_DATE, products_test.end_date)
   and nvl (products.ACTUAL_RETURN_DATE, products.end_date) 
    >= products_test.start_date
   and products.product_no 
    <> products_test.product_no

そして、これがSqlFiddleです。

編集: ROWIDを使用するバージョン:

select *
  from PRODUCTS
 inner join products products_test
    on products.PRODUCT_NO_REGISTRATION_NO 
     = products_test.PRODUCT_NO_REGISTRATION_NO
   and products.start_date 
    <= nvl (products_test.ACTUAL_RETURN_DATE, products_test.end_date)
   and nvl (products.ACTUAL_RETURN_DATE, products.end_date) 
    >= products_test.start_date
   and products.rowid
    <> products_test.rowid

2番目のSQLフィドル

明確化後の更新:製品の開始日と終了日の最小範囲と最大範囲をextendedレコードでカウントし、product_noとproduct_no_registration_noをテストして、範囲の重複について2つのストリームを比較し、自己参照を削除します。

with extended as
(
  select PRODUCT_NO, 
         PRODUCT_NO_REGISTRATION_NO, 
         min (START_DATE) as start_date,
         max (nvl (ACTUAL_RETURN_DATE, END_DATE)) as end_date
    from products
   group by PRODUCT_NO, PRODUCT_NO_REGISTRATION_NO
)
select e1.PRODUCT_NO_REGISTRATION_NO,
       e1.PRODUCT_NO,
       e1.start_date,
       e1.end_date,
       e2.PRODUCT_NO "PRODUCT_NO - CLASH",
       e2.start_date "START_DATE - CLASH",
       e2.end_date "END_DATE - CLASH"
  from extended e1
 inner join extended e2
    on e1.PRODUCT_NO_REGISTRATION_NO
     = e2.PRODUCT_NO_REGISTRATION_NO
   and e1.start_date <= e2.end_date
   and e1.end_date >= e2.start_date
-- Remove self-references
   and not
   (
           e1.PRODUCT_NO = e2.PRODUCT_NO
       and e1.PRODUCT_NO_REGISTRATION_NO 
         = e2.PRODUCT_NO_REGISTRATION_NO
   )

3番目のSQLフィドル

于 2012-07-30T11:53:16.213 に答える