2013-02-23 197 views
-1

我有一個字段有時包含像串以下:2/23/2013 12:25:55~45拆分和分析數據

我需要串在拆分〜並確定是否還剩下些什麼的〜是一個有效的日期時間值〜的正確值是一個有效的整數。基本上我想返回的是否是這些條件是正確的真/假。

請記住,該字段可能包含空值,可能包含任何其他類型的數據,並且可能包含多個波形符號。在所有情況下,我需要返回false。我需要返回true的唯一時間是該字段包含日期/時間值,單個代字號和整數。

+0

好的...和[你試過什麼](http://www.whathaveyoutried.com)? – Kermit 2013-02-23 19:30:06

+0

什麼版本的sql server?對於T-SQl字符串函數和T-SQl日期函數的快速Google,現在可以完成此操作。 – 2013-02-23 19:32:57

回答

2

在SQL Server中,你可以這樣做:

select (case when col like '%~%' 
      then (case when isdate(left(col, charindex('~', col) - 1)) = 1 and 
          isnumeric(substring(col, charindex('~', col)+1, 1000)) = 1 and col not like '%~%.%' and col not like '%~%e%' 
         then 1 
         else 0 
        end) 
      else 0 
     end) as IsFunkyFormat, substring(col, charindex('~', col)+1, 1000), left(col, charindex('~', col) - 1) 

的巢式病例是爲了防止錯誤時,未找到的分隔符。 not like表達式旨在排除不是整數的數字格式。

+0

我正在處理這個問題的答案。我剛剛測試了您的解決方案,並注意到如果輸入字符串是單個空格或空字符串,則會出現錯誤。 – 2013-02-23 21:24:51

+0

@Gasastros。 。 。當我測試這些值時,它正確返回「0」。它也爲''〜'返回零,所以我不知道你指的是什麼。 – 2013-02-23 21:29:12

+0

我的歉意。正是這個「導致錯誤的」(Data,charindex('〜',Data) - 1)「,這不是真正的解決方案,而僅僅是測試代碼。 – 2013-02-23 21:33:17

0

這個問題比看起來更復雜,因爲它很容易出錯,或者以現在適用於您的給定數據集的方式編寫,但無法爲其他數據集工作。

如果這是您存儲在數據庫中的數據,我強烈建議您瞭解數據庫規範化。規範化的一個原則是你只在一列中存儲一個值。在這種情況下,您將日期時間和整數值存儲在同一列中。將數據存儲在多個列中會好得多。這就是說,我知道有些時候您需要將一些原始數據導入數據庫。通常情況下,我們無法控制我們提供的原始數據,因此我們必須處理SQL體操。在這種特殊情況下,有幾種不同類型的後翻將會很有用。

  1. 確定字符串中的字符數。
  2. 在代字號上分割數據。
  3. 確保其中一個值是日期時間
  4. 確保其他值是整數。

只有4項中的1項內置到SQL Server中。有一個函數名稱IsDate接受一個字符串參數,並返回一個位,指示該字符串表示的日期是否可以轉換爲日期。

要確定您的字符串〜的數量,關鍵是要確定與波浪的字符串的長度和字符串的長度沒有波浪的。我們能確定哪些行包含單個波浪做這個:

When Len(Data) = Len(Replace(Data, '~', '')) + 1 

另一個棘手的問題,解決的是,以確定是否一個字符串代表一個整數。有多種方法可以做到這一點,但我最喜歡的方法是將硬編碼值連接到數據,然後測試數字。例如,對於字符串1e4,IsNumeric函數將返回true,因爲e表示科學記數法,1e4可以解釋爲1000。所以,如果你這樣做:

IsNumeric(Data + 'e0') 

這將返回科學記數法錯誤,因爲數據可能會像1E4,這將連接到「E0」得到「1e4e0」,這是不是數字。同樣,我們可以將.0連接到字符串以檢查分數。如果你的數據是45.2(它是數字的),並且你將它串聯起來,你會得到'45.0.0',這不是數字。您還可以在測試中添加' - '以檢查正數。 '-20'是數字,但' - '+'-20'(即' - 20')不是數字。

Select YourColumnHere, 
     Len(Replace(YourColumnHere, '~', '')) + 1, 
     Case When Len(YourColumnHere) = Len(Replace(YourColumnHere, '~', '')) + 1 
      Then 
        Case When IsDate(Left(YourColumnHere, CharIndex('~', YourColumnHere)-1)) = 1 
         Then 
           Case When Right(YourColumnHere, Len(YourColumnHere)-CharIndex('~', YourColumnHere)) > '' 
            Then IsNumeric('-' + Right(YourColumnHere, Len(YourColumnHere)-CharIndex('~', YourColumnHere)) + '.0e0') 
            Else 0 
            End 
         Else 0 
         End 
      Else 0 
      End 
From YourTableNameHere