2017-07-26 2 views
0

redaktionell aufbereitete Fragen:Struggling mit bedingter Logik

Ich kann die bedingte Logik für meine Frage scheinen, um herauszufinden.

Ich bin mir sicher, dass das einfach ist, aber ich habe meine Räder zu lange gedreht - es ist nur einer dieser Tage.

Jede Hilfe wird immer geschätzt.

CURRENT QUERY:

SELECT 
    r.WidgetPK 
    ,r.WidgetName 
    ,r.WeightRateFlag      [WeightRateFlag] 
    ,r.Rate         [Rate] 
    ,r.Breakpoint       [Breakpoint] 
    ,MAX(ISNULL(f.ShippingFee,0))   [ShippingFee] 
    ,MAX(ISNULL(f.OtherFee,0))    [OtherFee] 
    ,MAX(r.weight)       [Weight] 
FROM 
    #Rates r 
    LEFT JOIN #Fees f ON f.WidgetPK = r.WidgetPK 

ich die GROUP BY links der Einfachheit halber aus.

Wenn das WeightRateFlag in jeder Zeile für jedes WidgetPK eine 1 enthält, werden alle Zeilen mit einer 0 nicht zurückgegeben. Wenn das WeightRateFlag keine Zeilen mit einer 1 enthält, werden ALLE Zeilen zurückgegeben.

Entschuldigung die ursprüngliche Frage war nicht klar - Suchen helfen nicht und ich fragte einen Mitarbeiter. Ich denke, mein Problem könnte nur sein, dass ich hier und bei meinen Recherchen die falsche Frage stelle.

+2

Bitte geben Sie eine [mcve] (dh Eingabe, erwartete Ausgabe und Abfrage, die Sie bisher haben) und markieren Sie Ihre RDBMS-Plattform. – Igor

+1

Erwägen Sie die Verwendung einer UNION Alle, erste Abfrage erhält die mit einer 1 und die zweite Abfrage schließt alle Datensätze aus, die eine haben 1 – HLGEM

+0

@HLGEM eine UNION ALL ist, was mich zu diesem Punkt die #Rates Temp-Tabelle ist die Union von 2 anderen Tabellen. Ich habe die Tabellen weder erstellt, noch habe ich Bearbeitungsmöglichkeiten. Die meisten WidgetPKs sind in der ersten Tabelle in der UNION und eine Handvoll sind in der zweiten, aber wenn sie in der zweiten sind, sind sie auch in der ersten – DRT

Antwort

1
SELECT 
r.WidgetPK 
,r.WidgetName 
,r.WeightRateFlag      [WeightRateFlag] 
,r.Rate         [Rate] 
,r.Breakpoint       [Breakpoint] 
,MAX(ISNULL(f.ShippingFee,0))   [ShippingFee] 
,MAX(ISNULL(f.OtherFee,0))    [OtherFee] 
,MAX(r.weight)       [Weight] 
FROM 
#Rates r 
LEFT JOIN #Fees f ON f.WidgetPK = r.WidgetPK 
WHERE r.WeightRateFlag = 1 
UNION ALL 
SELECT 
r.WidgetPK 
,r.WidgetName 
,r.WeightRateFlag      [WeightRateFlag] 
,r.Rate         [Rate] 
,r.Breakpoint       [Breakpoint] 
,MAX(ISNULL(f.ShippingFee,0))   [ShippingFee] 
,MAX(ISNULL(f.OtherFee,0))    [OtherFee] 
,MAX(r.weight)       [Weight] 
FROM 
#Rates r 
LEFT JOIN #Fees f ON f.WidgetPK = r.WidgetPK 
WHERE r.WeightRateFlag = 0 
AND NOT EXISTS (SELECT * FROM #rates r2 WHERE r2WeightRateFlag =1 AND r.WidgetName = r2.WidgetName) 
+0

+1 Danke das funktioniert - ich muss vielleicht Feinabstimmung es, weil es ein nimmt Performance-Hit, aber das ist auf dem richtigen Weg. – DRT

+0

Höchstwahrscheinlich können Sie etwas Ähnliches tun, indem Sie stattdessen #rates erstellen. Alternativ können temporäre Tabellen indiziert werden. – HLGEM

0

Ein bisschen kompliziert aussehende, aber CTEs können sehr hilfreich sein. Außerdem sollten sie ziemlich gut mit dem Optimierer funktionieren. Ändern Sie für die benötigten Spalten.

/* TEST DATA SETUP */ 
IF OBJECT_ID(N'tempdb..#t1') IS NOT NULL 
BEGIN 
    DROP TABLE #t1 
END 
CREATE TABLE #t1 (WidgetPK int, col1 varchar(19), WeightRateFlag bit, ShippingFee money, OtherFee money, [Weight] int); 
INSERT INTO #t1 (WidgetPK, col1, WeightRateFlag, ShippingFee, OtherFee, [Weight]) 
VALUES 
     (1, 'showme1', 1, 9, 1, 1) 
    , (1, 'noshow2', 0, 2, 9, 2) 
    , (1, 'noshow3', 0, 1, 2, 9) 
    , (2, 'showme1', 1, 9, 9, 9) 
    , (3, 'showme1', 0, 1, 9, 1) 
    , (3, 'showme2', 0, 9, 9, 9) 
    , (3, 'showme3', 0, 9, 1, 9) 
; 

/* QUERY STARTS HERE */ 
WITH cte1 AS (
    SELECT x1.* 
    FROM (
     SELECT #t1.WidgetPK, #t1.col1, #t1.WeightRateFlag, #t1.ShippingFee, #t1.OtherFee, #t1.[Weight] 
      , RANK() OVER (PARTITION BY #t1.WidgetPK ORDER BY #t1.WeightRateFlag DESC) AS rn 
     FROM #t1 
    ) x1 WHERE x1.rn = 1 

) 
, cte2 AS (
    SELECT cte1.WidgetPK 
     , MAX(cte1.ShippingFee) AS ShippingFee 
     , MAX(cte1.OtherFee) AS OtherFee 
     , MAX(cte1.[Weight]) AS [Weight] 
    FROM cte1 
    GROUP BY cte1.WidgetPK 
) 
SELECT cte1.WidgetPK, cte1.col1, cte1.WeightRateFlag, cte2.ShippingFee, cte2.OtherFee, cte2.[Weight] 
FROM cte1 
LEFT OUTER JOIN cte2 ON cte1.WidgetPK = cte2.WidgetPK 
; 
Verwandte Themen