У меня есть следующая хранимая процедура, которая вычисляет максимальные значения для нескольких столбцов.Я достиг того же результата, используя длительный выбор объединения, однако меня просто интересует разница в производительности.Используя параметр SQL направления C # либо выходного, либо возвращаемого значения, я хотел бы вернуть только значение оператора select, помеченного как "- НЕОБХОДИМО ПОЛУЧИТЬ ЭТО ЗНАЧЕНИЕ ВЕРНУТО".
Я попытался создать переменную OUTPUTзатем используйте синтаксис SET для сохранения значения, затем синтаксис RETURN.Но безрезультатно.Получил ошибки, которые мне нужны для создания переменных, которые уже есть.Я не понимаю объем переменных, кажется.(Тем временем я удалил это из кода)
Вот мой SP:
CREATE PROCEDURE sp_GetMaximumMax
@FromDate DateTime,
@ToDate DateTime,
@TableName VarChar(150)
AS
DECLARE @SQL NVARCHAR(512), @ColumnName VARCHAR(150)
DECLARE @Result TABLE (Result int)
DECLARE read_cursor CURSOR FOR
SELECT column_name FROM INFORMATION_SCHEMA.COLUMNS
WHERE TABLE_NAME = @TableName
AND (column_name != 'id' AND column_name !='time' AND column_name !='no')
OPEN read_cursor;
FETCH NEXT FROM read_cursor INTO @ColumnName;
SET @SQL = 'SELECT MAX(['+@ColumnName+']) FROM '+@TableName+' WHERE [time] BETWEEN '''+CONVERT(VARCHAR, @FromDate, 120)+''' AND '''+CONVERT(VARCHAR, @ToDate, 120)+'''';
WHILE @@FETCH_STATUS = 0
BEGIN
Print @SQL
INSERT @Result
EXEC(@SQL);
FETCH NEXT FROM read_cursor
END
-- NEED TO GET THIS VALUE RETURNED
SELECT MAX(Result) AS MaxVar from @Result
CLOSE read_cursor;
DEALLOCATE read_cursor;
При этом мой исправленный код:
CREATE PROCEDURE sp_GetMaximumAvg
@FromDate DateTime,
@ToDate DateTime,
@TableName VarChar(150)
AS
CREATE TABLE #Fields(FieldName VARCHAR(150)) -- store column names
CREATE TABLE #Data(FieldName DECIMAL) -- store max values
DECLARE @ColumnName VARCHAR(150)
DECLARE @SQL VARCHAR(512)
-- add fields into field table
INSERT INTO #Fields (FieldName) SELECT column_name FROM INFORMATION_SCHEMA.COLUMNS WHERE TABLE_NAME = @TableName AND (column_name != 'id' AND column_name !='time' AND column_name !='no')
DECLARE @Field VARCHAR(150)
DECLARE @MyOutput INT
DECLARE ReadDaRow CURSOR
FOR SELECT * FROM #Fields
OPEN ReadDaRow
FETCH ReadDaRow INTO @Field
WHILE(@@FETCH_STATUS=0) BEGIN
SET @SQL = 'SELECT AVG(['+@Field+']) FROM '+@TableName+' WHERE [time] BETWEEN '''+CONVERT(VARCHAR, @FromDate, 120)+''' AND '''+CONVERT(VARCHAR, @ToDate, 120)+'''';
PRINT @SQL
INSERT INTO #Data EXEC(@SQL)
FETCH ReadDaRow INTO @Field
END
SELECT @MyOutput = MAX(FieldName) FROM #Data
RETURN @MyOutput
CLOSE ReadDaRow
DEALLOCATE ReadDaRow
DROP TABLE #Fields
DROP TABLE #Data
c # пример выполненияИП:
SqlCommand GetMaxCmd = new SqlCommand("sp_GetMaximumAvg", SQLConnection);
GetMaxCmd.CommandType = System.Data.CommandType.StoredProcedure;
GetMaxCmd.Parameters.Add("@FromDate", SqlDbType.DateTime).Value = DateTime.Parse(from_date);
GetMaxCmd.Parameters.Add("@ToDate", SqlDbType.DateTime).Value = DateTime.Parse(to_date);
GetMaxCmd.Parameters.Add("@TableName", SqlDbType.VarChar).Value = table_name;
SqlParameter Output = GetMaxCmd.Parameters.Add("@MyOutput", SqlDbType.SmallInt);
Output.Direction = ParameterDirection.ReturnValue;
try
{
GetMaxCmd.ExecuteNonQuery();
Max = Convert.ToInt32(Output.Value);
}
catch (NullReferenceException) { }
catch (FormatException) { }
catch (SqlException) { }