2012-05-01 15 views
3

私は作成しているMS SQLクエリを持っており、特定のレコードがバージョン番号に基づいて「新規」または「古い」カテゴリに該当するかどうかを判断する必要があります。演算子とバージョンより大きいまたは小さい

「VersionNum」という列があり、古いバージョンは2.75.99.99以降のバージョン番号ですが、新しいバージョンは2.76.00.00以降のバージョン番号です。列のデータ型はvarchar(20)です。

私は文字列のサブセットをX.XXから取り出し、これを10進数としてキャストすることを考えていました。そして、すべてのバージョンがX.XX小数点にキャストされると、select内のcase文で>または<を実行することによって古いものか新しいものかを判断できます。

これは、バージョン番号がどこになるのかを決めるのに正しいか考え方ですか?または、他にもいくつかの方法があります。私は、これに似た何かが他に必要であると想像しているので、私は尋ねるだけです。

編集:追加の問題が1つあります。 X.XX.XX.XX(2.76.00.00)ではなく、8.00.00という形式のいくつかのバージョンがあり、「古い」バージョンとみなされます。これは私が一度考えた以上にシステムを混乱させます。私は、5桁のバージョン(8.00.00)が常に古いとみなされているという情報を得ました。だから5桁があるときは、バージョンは古いです。だから私は次のようなケースステートメントを実行すると思います:

SELECT 
    Old = CASE WHEN LEN(VersionNum) < 10 THEN 1 
       WHEN CAST(SUBSTRING(VersionNum,1,4) AS DECIMAL(5,2)) < 1.52 
        AND LEN(VersionNum) >= 10 THEN 1 
       ELSE 0 
      END, 
    New = CASE WHEN CAST(SUBSTRING(VersionNum,1,4) AS DECIMAL(5,3)) >= 1.52 
        AND LEN(VersionNum) >= 10 THEN 1 
       ELSE 0 
      END 
FROM 
    VersionTable 

私のロジックは正しいですか?あるいは私は何かを逃している。長さの不平等は非常に迷惑です。

+0

バージョン番号を4バイト列に分割するオプションがありますか?それをキャストしようとするならば、Int32は十分に大きくなければなりません。 – Paparazzi

答えて

5

あなたはいつもそれが常にのみ4部を持つことになりますと仮定すると、整数などの「数」を表現することができます。

DECLARE @x VARCHAR(20); 

SELECT @x = '2.76.99.99'; 

SELECT 
v = PARSENAME(@x, 4) * 1000000 
    + PARSENAME(@x, 3) * 10000 
    + PARSENAME(@x, 2) * 100 
    + PARSENAME(@x, 1); 

結果:

2769999 
ビューを作成するのであれば

か複雑な解析/変換を行うのではなく、簡単な計算を使って比較することができます。テーブルには3つのしかオクテットを持っているいくつかの値を持つ場合

EDITコメント

に基づいて、なぜそれを修正しませんか?

UPDATE dbo.table SET col = col + '.00' 
    WHERE LEN(x) < 10; 

あなたがより正確になりたい場合は、次の

UPDATE dbo.table SET col = LTRIM(RTRIM(col)) + '.00' 
    WHERE LEN(LTRIM(RTRTIM(x))) - LEN(REPLACE(LTRIM(RTRIM(x)), '.', '')) = 3; 
+1

+1 - 新しいソリューション。ただし、 'PARSENAME'は最大4つの値でしか動作しません。 – JNK

+0

@JNKありがとう、将来の読者のために更新されました。 –

+0

私には1つの問題があります。現在、X.XX.XXの番号とX.X.XX.XXXの番号があります。これは問題をさらに混乱させるだけです。 5桁の値は古いとみなされ、7桁の値(3つのビルドバージョンの桁)は新しいものとみなされます。 – Tom

1

実際の問題は、必要な範囲に応じて、バージョン番号を一連のsmallint,int、またはbigintに分割することです。これを行うことができない場合は、潜在的にそれらのルックアップテーブルを作成することができますが、これははるかに厄介な解決策です。

あなたが持っていた場合は、言う:必要に応じて

CREATE TABLE Versions 
(MajorVersion int, 
MinorVersion int, 
Subversion int, 
Build int) 

は、その後、個々のフィールドを比較することができます。

+0

+1私はこれらのことを別々に保存する必要があることに同意しているからです。まだ、あるバージョンが別のバージョンよりも大きいかどうかを判断する計算は、やはり重要なものではありません。 –

+0

@AaronBertrand良い点。 – JNK

0

バージョン文字列の数字は、左側にゼロが追加され、その後、あなただけの比較文字列を使用することができた場合:「2.75.99.99」 < "2.76.00.00"。

これは、フォーマットがすべてのバージョンで一貫していると仮定して動作します。

+2

文字列として残した場合を除き、 '' 12.8.99 '<' 2.8.99'''は 'TRUE'を返します... – JNK

関連する問題