0

У меня есть функция SQL, которая принимает параметр как BIGINT, как показано ниже:Выполнение функции с несколькими значениями в одном параметре

FUNCTION [dbo].[fn_doc] 
(
    @DocID   bigint   
) 

Я хочу передать несколько DOc ID и хочу, чтобы получить результаты. За что я делаю так:

declare @DocID bigint 
SET @DocID = (2949146,2949148,2949149,14016926,14025278,14016928,14016928,14025280,14025280) 
select * from [fn_doc] (@DocID) 

Мой вопрос, как выполнить функцию с несколькими значениями для одного параметра в этом случае?

+0

Исследование ** T ** возможно ** V ** alued ** P ** arameters онлайн. –

+0

Любой пример ссылки, пожалуйста, для этого конкретного сценария? – AskMe

+0

Все сценарии - это те же tbh. Если вам нужно передать список значений в качестве параметра функции или SP, используйте TVP. Это общий совет. Многое, что можно найти в Интернете, если вы ищете 'sql server table value parameter'. GL! –

ответ

0

Это не может работать

declare @DocID bigint 
SET @DocID = (2949146,2949148,2949149,14016926,14025278,14016928,14016928,14025280,14025280) 

переменная, объявленная в BIGINT не может нести ничего, кроме большого количества ...

Что вы пытаетесь передать это запятая delimitted строка, которая представляет собой Список номеров.

Для этого нет встроенных функций. Neiter IN -clause, ни любой вид JOIN будет делать это изначально.

У вас есть несколько вариантов

  • Динамический SQL для создания оператора выбора, как строки и использовать EXEC, чтобы получить результат (что-то вроде WHERE docid IN(100,200,300))
  • Создания таблицы (переменный, темпа или классического) , заполните его вашими значениями и используйте IN или JOIN в вашей функции (у этого будут проблемы с параллельными действиями!)
  • Создайте TYPE, чтобы передать его в виде таблицы
  • Используйте некоторую операцию разделения для получения производной таблицы. Для этой опции вы можете прочитать this answer (section "dynamic IN")

Вот post with list of approaches

0

быстро и грязно, но он должен работать :-) это пример для последнего предложения Shnugo в

CREATE FUNCTION [dbo].[fn_doc] (@DocID as bigint) 
RETURNS bigint 
AS 
BEGIN 
    RETURN @DocID 
END 

/* your function parameter is a comma seperated list */ 
DECLARE @Parameter VARCHAR(200) 
SET @Parameter = '2949146,2949148,2949149,14016926,14025278,14016928,14016928,14025280,14025280' 

/* start and end current parameter */ 
DECLARE @start int, @end int 
SET @start = 0 
SET @end = 1 

/* current parameter */ 
DECLARE @p NVARCHAR(200) 

WHILE @end > 0 
BEGIN 
    SET @end = CHARINDEX(',', @Parameter, @start) 
    IF @start < @end 
     IF ISNUMERIC(SUBSTRING(@Parameter, @start, @[email protected])) = 1 
      SET @p = SUBSTRING(@Parameter, @start, @[email protected]) 
      PRINT [dbo].[fn_doc] (@p) 
    SET @start = @end +1 
END 
+1

Это может быть * грязно * но - наверняка! - это не * быстро *. – Shnugo

0

Apparantly вы все еще не из леса. Поэтому я оставлю вас с примером.


Создать тип TABLE:

CREATE TYPE dbo.document_ids AS TABLE (
    document_id BIGINT 
); 
GO 

Если вы можете гарантировать, что только отдельные document_id значения будут переданы в качестве параметра, вы можете извлечь выгоду из определения первичного ключа на document_id поле:

CREATE TYPE dbo.document_ids AS TABLE (
    document_id BIGINT PRIMARY KEY 
); 
GO 

Создание функций, зависящих от что TABLE типа, один скалярная и одна таблица многозначных:

CREATE FUNCTION dbo.fn_doc_sv (
    @doc_ids dbo.document_ids READONLY 
) 
RETURNS BIGINT 
AS 
BEGIN 
    RETURN (SELECT SUM(document_id) FROM @doc_ids); 
END 
GO 

CREATE FUNCTION dbo.fn_doc_tv (
    @doc_ids dbo.document_ids READONLY 
) 
RETURNS TABLE 
AS 
    RETURN (SELECT document_id FROM @doc_ids); 
GO 

Использование обеих функций:

DECLARE @doc_ids dbo.document_ids; 
INSERT INTO @doc_ids(document_id)VALUES(2949146),(2949148),(2949149),(14016926),(14025278),(14016928),(14016928),(14025280),(14025280); 

SELECT dbo.fn_doc_sv(@doc_ids); 

SELECT * FROM dbo.fn_doc_tv(@doc_ids); 

Надежда, что делает его более понятным для вас.

 Смежные вопросы

  • Нет связанных вопросов^_^