2013-07-19 23 views
2

我想在SQL SERVER中處理一些數據,做一些QA並同時得到'答案'。SQL Server通過分組檢查非等效列/行

該表代表一個測試,如果測試沒有給出100%的匹配,則它重複運行。

在該表中以下代碼都適用,他們是按照優先級的升序: 1)-99測試被跳過 2)00測試不是100%匹配 3)任何> 00是100%匹配(例如01,02,01-01等)

所以我需要做幾件事情。首先,對於每個SampleID,我需要挑選哪裏01> 00> -99 其次,我需要知道任何測試是否有100%的匹配(例如#3)並且測試不同意。一個例子是11-0010-P1(下圖),其中Run2 = 01和Run3 = 02

我有點得到了第一部分的代碼,但是我無法獲得ROWNUMBER()的最大部分查詢。

我真的被困在第二部分。

所有幫助將不勝感激!

DECLARE @TempTable TABLE (SampleID varchar(10), TestRun int, TestResult varchar(max)) 

    INSERT INTO @TempTable VALUES('11-0003-P1', 1,'-99')  
    INSERT INTO @TempTable VALUES('11-0004-P1', 1, '00')  
    INSERT INTO @TempTable VALUES('11-0005-P1', 1, '01') 
    INSERT INTO @TempTable VALUES('11-0007-P1', 1,'-99')  
    INSERT INTO @TempTable VALUES('11-0007-P1', 2, '00')  
    INSERT INTO @TempTable VALUES('11-0007-P1', 3, '00')  
    INSERT INTO @TempTable VALUES('11-0008-P1', 1,'-99') 
    INSERT INTO @TempTable VALUES('11-0008-P1', 2, '02') 
    INSERT INTO @TempTable VALUES('11-0008-P1', 3, '02')  
    INSERT INTO @TempTable VALUES('11-0009-P1', 1, '00') 
    INSERT INTO @TempTable VALUES('11-0009-P1', 2, '07') 
    INSERT INTO @TempTable VALUES('11-0009-P1', 3, '07') 
    INSERT INTO @TempTable VALUES('11-0010-P1', 1, '00') 
    INSERT INTO @TempTable VALUES('11-0010-P1', 2, '01') 
    INSERT INTO @TempTable VALUES('11-0010-P1', 3, '02')  

    SELECT SampleID, TestRun, TestResult, 
    ROW_NUMBER() OVER (PARTITION BY SampleID 
         ORDER BY 
          CASE TestResult 
          WHEN '-99' THEN 1 
          WHEN '00' THEN 2 
          ELSE 3 
          END 
         ) AS RowNumber 
    FROM @TempTable 
    ORDER BY SampleID, TestRun 

的結果應該是這樣的:

SampleID TestResult 
11-0003-P1 -99 
11-0004-P1 00 
11-0005-P1 01 
11-0007-P1 00 
11-0008-P1 02 
11-0009-P1 07 
11-0010-P1 Err 01:02 

**它會理想實際上給衝突值(例如01:02爲11-0010-P1),但不是完全必要, Err標誌將會正常。

+0

+1。 。 。順便說一句,這是一個很好的問題。您提供示例數據和腳本來測試! –

回答

1

你被窗口函數混淆,因爲你可以解決這個使用常規group by

select SampleId, 
     (case when max(TestResult) in ('-99', '00') then max(TestResult) 
      when max(TestResult) = min(case when TestResult not in ('-99', '00') then TestResult end) 
      then max(TestResult) 
      else 'Err '+min(case when TestResult not in ('-99', '00') then TestResult end)+':'+max(TestResult) 
     end) 
from TempTable 
group by SampleId; 

這裏有兩個重要的點。第一個是'-99'<'00'< xx字符串以及數字。因此,max()可以找到最後的測試結果。

第二個是找到「其他」值,其中有多個值。爲此,查詢使用條件最小值 - 即查找不包括'-99'和'00'的最小值。

SQL小提琴是here,這就是爲什麼我將@TempTable更改爲TempTable

+0

謝謝!這太棒了 – user918967

0

以下查詢會給你最大的行號,但我不明白'Err'的條件是否可以詳細說明?

查詢:

select SampleID, TestResult 
from (
SELECT SampleID, TestRun, TestResult, 
    ROW_NUMBER() OVER (PARTITION BY SampleID 
         ORDER BY 
          CASE TestResult 
          WHEN '-99' THEN 1 
          WHEN '00' THEN 2 
          ELSE 3 
          END desc 
         ) AS RowNumber 
    FROM @TempTable 
) t 
where RowNumber = 1 
ORDER BY SampleID, TestRun 
+0

當它 - 我弄錯了(錯誤功能)。它應該閱讀02:07(非等價的行) – user918967

+0

不,我做它正確。如果你看看11-0010-P1,你會注意到Run 2不等於Run 3. – user918967