整数のリストを値のテーブルに分割するユーザー定義関数があります。これを使用して入力を解析し、特定のタイプまたはステータスのセットのレコードのセットを選択しています。
これは機能します:
select * from RequestStatus
where RequestStatusUID in (select [value] from dbo.SplitIDs('1,2,3', ','))
これはしません:
select * from Requests
where RequestStatusUID in (select [value] from dbo.SplitIDs('1,2,3', ','))
Requestsクエリは、「varchar値「1,2,3」をデータ型intに変換するときに変換に失敗しました。 」というエラーを返します。両方のテーブルのRequestStatusUIDはint列です。Explainの両方の計画は私には同じように見えます。この関数は、無関係のクエリでもまったく同じように機能します。私が知る限り、問題があるのはRequestsテーブルだけです。
CREATE TABLE [dbo].[Requests] (
[RequestUID] int IDENTITY(1,1) NOT NULL,
[UserUID] int NOT NULL,
[LocationUID] int NOT NULL,
[DateOpened] date NULL,
[DateClosed] date NULL,
[RequestStatusUID] int NOT NULL,
[DiscussionUID] int NULL,
[RequestTypeUID] int NOT NULL,
[RequestNo] varchar(16) NOT NULL,
[LastUpdateUID] int NOT NULL,
[LastUpdated] date NOT NULL,
CONSTRAINT [PK_Requests] PRIMARY KEY NONCLUSTERED([RequestUID])
varcharsを返す別の関数を使用し、RequestStatusUID列もvarcharに変換すると機能します。
select * from Requests
where cast(RequestStatusUID as varchar(4)) in (select [value] from dbo.Split('1,2,3', ','))
参考までに、私が使用しているSplitIDs関数(Arnold Fribbleのソリューションの修正バージョン)。Split関数は、キャストがなくても最後のintと同じです。
ALTER FUNCTION [dbo].[SplitIDs] ( @str VARCHAR(MAX), @delim char(1)=',' )
RETURNS TABLE
AS
RETURN
(
with cte as (
select 0 a, 1 b
union all
select b, cast(charindex(@delim, @str, b) + 1 as int)
from cte
where b > a
)
select cast(substring(@str,a,
case when b > 1 then b-a-1 else len(@str) - a + 1 end) as int) [value]
from cte where a >0
)
文字列に変換するソリューションを使用できますが、そもそもなぜこれが失敗するのかを知りたいのです。