MSSQL - Представление данных при динамических именах столбцов
-
09-09-2019 - |
Вопрос
Я представляю окончательному органу оценки баллы для сотрудников.Каждая строка - это данные сотрудника, и поскольку категории, подлежащие оценке, могут меняться от периода к периоду, имена столбцов не могут быть жестко запрограммированы в хранимых процедурах.Я уже разработал следующее решение.
1 Создайте временную таблицу
2 Динамически используйте команду Alter Table для добавления всех применимых столбцов (сохраненных в @ColumnNames).
3 Используйте динамический SQL внутри курсора, чтобы написать вставку для каждого сотрудника, который получает правильные оценки (т. е. N сотрудников означает N вставок)
(SELECT @ECMScores = COALESCE(@ECMScores + ',', '') + CAST(EIS.ECMScore AS NVARCHAR(1000)) (FROM...))
SET @SQLString = ''
SET @SQLString = @SQLString + 'INSERT INTO #ResultSet ('
SET @SQLString = @SQLString + 'EvaluationScoreID,'
SET @SQLString = @SQLString + 'EmployeeID,'
SET @SQLString = @SQLString + 'EmployeeName,'
SET @SQLString = @SQLString + @ColumnNames
SET @SQLString = @SQLString + ') '
SET @SQLString = @SQLString + 'VALUES ('
SET @SQLString = @SQLString + ''+CAST(@EvaluationScoreID AS NVARCHAR(MAX))+','
SET @SQLString = @SQLString + ''+CAST(@EmployeeID AS NVARCHAR(MAX))+','
SET @SQLString = @SQLString + '"'+@EmployeeName+'",'
SET @SQLString = @SQLString + @ECMScores
SET @SQLString = @SQLString + ')'
EXECUTE sp_executesql @SQLString
Проблема в том, что это занимает примерно 1 секунду на каждые 100 сотрудников.Это быстро становится неприемлемым…
Есть ли у кого-нибудь идеи получше о том, как действовать дальше?Удаление курсора (очевидно) и использование одной вставки (возможно, Select into) - это моя первая идея, возможно, чтение из динамически созданной XML-переменной…
Спасибо,
Решение
не храните данные в схеме
создавайте таблицы, подобные этой:
Assignment
AssignmentID int not null primary key identity(1,1)
AssignmentName varchar(50) not null
AssignmentDate datetime not null
etc..
Score
ScoreID int not null primary key identity(1,1)
EmployeeID int not null
AssignmentID int not null
ScoreValue int not null
Employee
EmployeeID int not null primary key identity(1,1)
EmployeeName varhar(100) not null
etc..
теперь вы можете создавать "назначения" и вставлять "оценки" без создания динамических запросов, потому что ваши столбцы всегда меняются.теперь ваши столбцы останутся прежними, а данные изменятся.
Другие советы
Прежде всего, была бы у вас возможность изменить структуру базы данных?Если я правильно понимаю, поле EIS.ECMScore EIS.ECMScore содержит несколько значений, что является нарушением правил нормализации.Лично я бы изменил дизайн таблицы EIS и нормализуйте его, так как это значительно облегчило бы вашу задачу.