sql >> Databasteknik >  >> RDS >> Oracle

Lösningsprocedur utan parametrar

Förutom kommentarerna och svaren du redan har fått, tror jag att du har överkomplicerat ditt förfarande enormt. Du gör saker mycket procedurmässigt, snarare än att tänka i uppsättningar som du borde vara. Du får också de aggregerade kolumnerna i tre frågor som är i huvudsak identiska (t.ex. samma tabeller, sammanfogningsvillkor och predikat) - du kan kombinera dem alla för att få de tre resultaten i en enda fråga.

Det ser ut som att du försöker infoga i tabellen för klienthistoriska köp om en rad inte redan finns för den klienten, annars uppdaterar du raden. Det skriker omedelbart "MERGE statement" till mig.

Om jag kombinerar allt detta, tror jag att din nuvarande procedur bara bör innehålla ett enda sammanslagningsuttryck:

MERGE INTO clienthistoricalpurchases tgt
  USING (SELECT clients.client_id,
                COUNT(DISTINCT od.productid) distinct_products,
                COUNT(od.productid) total_products,
                SUM((od.unitprice * od.quantity) - od.discount) proposed_new_balance
         FROM   orderdetails od
         INNER  JOIN orders
         ON     orderdetails.orderid = orders.orderid
         INNER  JOIN clients
         ON     orders.clientid = clients.clientid
         GROUP BY clients.client_id) src
  ON (tgt.clientid = src.client_id)
WHEN NOT MATCHED THEN
  INSERT (tgt.clientid,
          tgt.distinctproducts,
          tgt.totalproducts,
          tgt.totalcost) 
  VALUES (src.clientid,
          src.distinct_products,
          src.total_products,
          src.proposed_new_balance)
WHEN MATCHED THEN
  UPDATE SET tgt.distinctproducts = src.distinct_products,
             tgt.totalproducts = src.total_products,
             tgt.totalcost = src.proposed_new_balance;

Jag har dock en del oro över din nuvarande logik och/eller datamodell.

Det verkar som om du förväntar dig att högst en rad per kund-id ska visas i kundhistoriska inköp. Vad händer om ett kund-ID har två eller flera olika beställningar? För närvarande skulle du skriva över alla befintliga rader.

Dessutom, vill du verkligen tillämpa denna logik på alla beställningar varje gång den körs?



  1. MySQL om rad finns uppdatera annars infoga

  2. Integrera sökning på en webbplats där backend är MYSQL

  3. Eliminera underfrågan för genomsnittligt numeriskt värde

  4. JDBC :returnerar flera resultatuppsättningar via en enda databasanrop - fungerar inte för Oracle