2012-01-24 39 views
1

在這段MS Access Code中,我試圖獲取客戶註冊的MAX日期。首先,我必須轉換日期,以便它可以使用聚合函數。不幸的是,日期列中有些區域爲空。如何解決或補救錯誤:無效使用空值?

我收到錯誤由於某些記錄缺失日期而無效使用空

我該如何補救,有沒有解決辦法?

下面是代碼:

SELECT CUSTOMER.FIRST_NAME, 
    MAX(DateSerial(CInt(Left([CUSTOMER.SIGNUP_DATE],4)),CInt(Mid([CUSTOMER.SIGNUP_DATE],5,2)),CInt(Right([CUSTOMER.SIGNUP_DATE],2)))) AS SIGN_DATE, 
    (DateSerial(CInt(Left([CUSTOMER.LEAVE_DATE],4)),CInt(Mid([CUSTOMER.LEAVE_DATE],5,2)),CInt(Right([CUSTOMER.LEAVE_DATE],2)))) AS LEV_DATE 
FROM CUSTOMER 
WHERE ((DateSerial(CInt(Left([CUSTOMER.SIGNUP_DATE],4)),CInt(Mid([CUSTOMER.SIGNUP_DATE],5,2)),CInt(Right([CUSTOMER.SIGNUP_DATE],2)))) <=Date()) 
    AND ((DateSerial(CInt(Left([CUSTOMER.LEAVE_DATE],4)),CInt(Mid([CUSTOMER.LEAVE_DATE],5,2)),CInt(Right([CUSTOMER.LEAVE_DATE],2)))) =#012/31/2012#) 
GROUP BY 
    CUSTOMER.FIRST_NAME, 
    CUSTOMER.SIGNUP_DATE, 
    CUSTOMER.LEAVE_DATE; 
+2

建議:創建一個視圖,說名爲'CurrentCustomers'那用空'LEAVE_DATE'過濾掉客戶,然後定位VIEW。但是你真的應該用實際的時間值永久替換那些與文本一樣的日期列,而不是試圖在飛行中這樣做。 – onedaywhen

+0

謝謝!我正在考慮首先濾除空值而不是添加Aggregate,表格連接到Access,因此我必須將它們的文本值轉換爲日期。 – Asynchronous

+1

當你把這些名字放在括號裏時,它能正常工作嗎?不應該例如'[CUSTOMER.SIGNUP_DATE]'是[CUSTOMER]。[SIGNUP_DATE]'而不是?我不是一個MS Access人員,所以請原諒,如果這似乎是一個愚蠢的問題。 –

回答

1

你SIGNUP_DATE字段包含日期爲這種格式的字符串: 「20120131」。因此,您使用Left(),Mid()和Right()函數來分割年,月和日子字符串,將它們轉換爲帶有CInt()的數字,最後將這些數字提供給DateSerial()。

如果只有您的日期字符串在3個部分之間包含合適的分隔符,則可以簡單地將字符串提供給CDate(),例如CDate(「2012-01-31」)。所以我建議你在查詢中向字符串添加分隔符並將其提供給CDate()。

這是我的簡化客戶表:

id SIGNUP_DATE 
1 20120130 
2 
3 20120131 

該查詢轉換非空SIGNUP_DATE值日期/時間值,並丟棄行,其中SIGNUP_DATE爲Null(帶有ID = 2的行除外)。

SELECT 
    id, 
    CDate(Left(SIGNUP_DATE,4) & "-" 
     & Mid(SIGNUP_DATE,5,2) & "-" & 
     Right(SIGNUP_DATE,2)) 
     AS SIGN_DATE 
FROM CUSTOMER 
WHERE SIGNUP_DATE Is Not Null; 

然後獲得最大值很簡單。

SELECT Max(q.SIGN_DATE) AS MaxOfSIGN_DATE 
FROM (
     SELECT 
      id, 
      CDate(Left(SIGNUP_DATE,4) & "-" 
       & Mid(SIGNUP_DATE,5,2) & "-" & 
       Right(SIGNUP_DATE,2)) 
       AS SIGN_DATE 
     FROM CUSTOMER 
     WHERE SIGNUP_DATE Is Not Null 
    ) AS q; 

編輯:由於沒有樣本數據來測試對,我只是臨場發揮,並建議你試試這個查詢:

SELECT 
    q.FIRST_NAME, 
    #2012/12/31# AS LEV_DATE, 
    Max(q.SIGN_DATE) AS MaxOfSIGN_DATE 
FROM (
     SELECT 
      FIRST_NAME, 
      CDate(Left(SIGNUP_DATE,4) & "-" 
       & Mid(SIGNUP_DATE,5,2) & "-" & 
       Right(SIGNUP_DATE,2)) 
       AS SIGN_DATE 
     FROM CUSTOMER 
     WHERE 
      SIGNUP_DATE Is Not Null 
      AND LEAVE_DATE = "20121231" 
    ) AS q 
GROUP BY 
    1, 
    2; 
+0

非常感謝您的寶貴意見!對於MAX函數,我不試圖選擇具有最高日期的CUSTOMER。我試圖選擇最高註冊日期,如果客戶多於一個。假設客戶有兩個日期。 2012年1月1日和2012年2月1日,然後我想要最高,你的代碼給了我整個專欄中的最高日期。 – Asynchronous

+0

是的,我以這種方式呈現,因爲我很容易做到。使用相同的原則並將它們應用於原始GROUP BY查詢中---爲每個組計算Max(),而不是僅爲查詢返回的完整記錄集計算一次。 – HansUp

+0

是的,只有那些日期值存在時,記錄纔會啓動。最初,MAX的整個想法是獲得最高的日期。那是當我得到空錯誤。但是記錄可以被跳過。 這是一個非常簡單的查詢。如果它是空的,跳過它,獲得最高的日期。 是的,LEAVE_DATE可以保持這種方式,請記住,我正在創建異常情況以供學習。 – Asynchronous

相關問題