Я настроил тестовую базу данных и консольное приложение, чтобы подтвердить следующее:
Имеется база данных SQL со следующей функцией:
CREATE FUNCTION ufn_GTFO
(
@Guid as uniqueidentifier
)
RETURNS VARCHAR(100)
AS
BEGIN
-- Declare the return variable here
DECLARE @Result as VARCHAR(100)
-- Add the T-SQL statements to compute the return value here
SELECT @Result = 'This is a test'
-- Return the result of the function
RETURN @Result
END
GO
И следующая таблица:
CREATE TABLE [dbo].[Test](
[PKey] [int] IDENTITY(1,1) NOT NULL,
[WFT] [uniqueidentifier] NULL,
CONSTRAINT [PK_Test] PRIMARY KEY CLUSTERED
(
[PKey] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY]
) ON [PRIMARY]
Скалярная функция ufn_GTFO обычно компонуется, так что следующий C #:
static void ConcreteTest()
{
DataClasses1DataContext db = new DataClasses1DataContext();
var q = from t in db.Tests
select new { t.PKey, GTFO = db.ufn_GTFO(t.WFT) };
var p = q.ToArray();
}
Переводится на следующий SQL:
SELECT [t0].[PKey], [dbo].[ufn_GTFO]([t0].[WFT]) AS [GTFO] FROM [dbo].[Test] AS [t0]
Однако, если я использую интерфейс refactor -> extract в DataContext и использую его экземпляр:
static void InterfaceTest()
{
IDataClasses1DataContext db = new DataClasses1DataContext();
var q = from t in db.Tests
select new { t.PKey, GTFO = db.ufn_GTFO(t.WFT) };
var p = q.ToArray();
}
Я получаю следующий SQL, и вызовы ufn_GTFO происходят один раз для каждой записи, так как .ToArray () перечисляет результаты.
SELECT [t0].[PKey], [t0].[WFT] AS [guid]
FROM [dbo].[Test] AS [t0]
Итак, мой вопрос: почему это происходит и что я могу сделать, чтобы предотвратить это, все еще используя интерфейс?
Обновление 1: Я сравнил IL, сгенерированный для конкретного метода, с методом интерфейса, и они отличаются только ссылкой на интерфейс и класс отображения, сгенерированный компилятором, который, кажется, не иметь какое-либо отношение к результату.