1

データベースと比較する必要がある値のコンマ区切りリストを渡しています

渡す値の例を次に示します。

@orgList = "1123, 223%, 54%"

ワイルドカードを使用するには、私がしなければならないと思いますLIKEが、クエリは長時間実行され、14 行しか返されません (結果は正しいですが、おそらく結合を間違って使用しているため、永遠にかかっています)

改善できますか?

これは私が今していることです:

declare @tempTable Table (SearchOrg nvarchar(max) )

insert  into @tempTable
   select * from dbo.udf_split(@orgList) as split 

-- this splits the values at the comma and puts them in a temp table

-- then I do a join on the main table and the temp table to do a like on it.... 
-- but I think it's not right because it's too long. 

select something 
from maintable gt
join @tempTable tt on gt.org like tt.SearchOrg
where
    AYEAR= ISNULL(@year, ayear)
    and (AYEAR >= ISNULL(@yearR1, ayear) and ayear <= ISNULL(@yearr2, ayear))
    and  adate = ISNULL(@Date, adate)
    and (adate  >= ISNULL(@dateR1, adate) and adate <= ISNULL(@DateR2 , adate))

最終結果は、maintable.orgが 1123 であるか、223 で始まるか、または 554 で始まるすべての行になります。

私の日付の狂気の理由は、ストアドプロシージャが年、年の範囲、特定の日付、および日付の範囲のみをチェックする場合があるためです...使用されていないものはすべて null として渡されます。

多分問題はそこにありますか?

4

3 に答える 3

1

クエリの最適化が難しい場合があります。問題の一部は、where条項の内容です。おそらく、最初にこれらをフィルタリングしてから、 を使用して結合しlikeます。または、結合を高速化してから、結果に対して完全なテーブル スキャンを実行することもできます。

SQL Server はlike、'abc%' の形式のステートメントを最適化する必要があります。つまり、ワイルドカードが最後にある場所です。(たとえば、ここmaintable.orgを参照してください。) したがって、 のインデックスから開始できます。幸いなことに、あなたの例はこの基準を満たしています。ただし、'%abc' (ワイルドカードが最初に来る) がある場合、最適化は機能しません。

whereインデックスが最適に機能するためには、句の条件も考慮する必要がある場合があります。つまり、インデックスを追加することは示唆的ですが、クエリの残りの部分ではインデックスを使用できない可能性があります。

さらに、これらのタイプの検索に対する最善の解決策は、SQL Server の全文検索機能を使用することです (こちらを参照)。

于 2013-02-27T14:14:27.503 に答える
1

次のようなことを試してください:

Declare @tempTable Table
(
   -- Since the column is a varchar(10), you don't want to use nvarchar here.
   SearchOrg varchar(20)
);

INSERT INTO @tempTable
SELECT * FROM dbo.udf_split(@orgList);

SELECT 
   something
FROM 
   maintable gt
WHERE
   some where statements go here
And
   Exists
   (
      SELECT 1
      FROM @tempTable tt
      WHERE gt.org Like tt.SearchOrg
   )
于 2013-02-27T14:03:10.213 に答える
1

オプションのフィルターを使用し、テーブル (!) によって駆動されるこのような動的クエリLIKEは、静的に知られているものがほとんどないため、最適化が非常に困難です。オプティマイザは非常に一般的な計画を作成する必要があります。

マグニチュートのオーダーでこれを高速化するには、次の 2 つの方法があります。

  1. で遊ぶOPTION (RECOMPILE)。コンパイルtimesが受け入れられる場合、これは少なくともすべてのオプションのフィルターを処理します (ただし、LIKE テーブルは処理しません)。
  2. コード生成とEXEC sp_executesqlコードを実行します。LIKE次のようになるように、すべての句を SQL にインライン化してクエリを作成します: (または が必要かWHERE a LIKE @like0 OR a LIKE @like1 ...どうかはわかりません)。これにより、オプティマイザは結合を取り除き、通常の述語のみを実行できます)。ORAND
于 2013-02-27T14:29:50.080 に答える