Есть ли способ запросить 135 различных таблиц в одном запросе? - PullRequest
8 голосов
/ 02 мая 2011

В нашей базе данных у нас есть 135 таблиц, у которых есть столбец с именем EquipmentId.Мне нужно запросить каждую из этих таблиц, чтобы определить, имеет ли какой-либо из них EquipmentId, равный определенному значению.Любой способ сделать это в одном запросе, вместо 135 отдельных запросов?

Большое спасибо.

Ответы [ 6 ]

6 голосов
/ 02 мая 2011

Вы просматриваете либо динамический SQL для генерации запросов ко всем таблицам и, возможно, объединения результатов, либо используете что-то вроде недокументированной sp_MSforeachtable хранимой процедуры.

sp_msforeachtable 'select * from ? where equipmentid = 5'
5 голосов
/ 02 мая 2011

Вы можете использовать запрос для создания запроса:

select  'union all select * from ' + name + 
             ' where EquipmentId = 42' + char(13) + char(10) 
from     sys.tables

Скопируйте результат, удалите первый union all и выполните запрос:)

1 голос
/ 03 мая 2011

Я предполагаю, что не все таблицы в БД имеют столбец EquipmentId. Если это допустимое предположение, тогда параметр @whereand параметра sp_msforeachtable поможет отфильтровать таблицы. Запрос ниже покажет все имена таблиц, которые указали EquipmentId. Имя таблицы будет показано столько раз, сколько строк в этой таблице имеют указанный идентификатор оборудования.

declare @EquipmentId int = 666

create table #Result (TableName sysname)

declare @command nvarchar(4000) = 
    'insert into #Result select ''?'' from ? where EquipmentId = ' + cast(@EquipmentId as varchar)

execute sp_msforeachtable
    @command1 = @command,
    @whereand = 'and o.id in (select object_id from sys.columns where name = ''EquipmentId'')'

select * 
from #Result 

drop table #Result 
1 голос
/ 02 мая 2011

Я бы выбросил их во временную таблицу или что-то подобное:

CREATE TABLE #TempTable (Equip NVARCHAR(50))
sp_msforeachtable 'INSERT INTO #TempTable (Equip) SELECT Equip FROM ?'
SELECT * FROM #TempTable
DROP TABLE #TempTable
0 голосов
/ 03 мая 2011

Это может быть реализовано с помощью LEFT JOIN.Сначала нам понадобится базовая таблица для хранения определенных значений ИД оборудования, которые мы ищем:

CREATE TABLE #CertainValues
(
    EquipmentID int
)
INSERT INTO #CertainValues(EquipmentID) VALUES (1)
INSERT INTO #CertainValues(EquipmentID) VALUES (2)
INSERT INTO #CertainValues(EquipmentID) VALUES (3)

Затем мы можем присоединить 135 известных таблиц к этой базовой таблице, используя ихсоответствующие поля [EquipmentID].Чтобы избежать проблем с кардинальностью (дублирование) из-за того, что [EquipmentID] появляется в нескольких строках одной таблицы, лучше использовать подзапрос для получения подсчетов по [EquipmentID] в каждой из 135 таблиц.Это также дает нам более значимый набор результатов, который показывает количество строк в таблице для каждого из определенных значений , которые мы ищем.Ниже приведен пример набора результатов:

EquipmentID  T001  T002  ...  T134  T135
-----------  ----  ----  ...  ----  ----
          1     0     1  ...     2     3 
          2     3     2  ...     1     0 
          3     0     0  ...     0     0 
0 голосов
/ 02 мая 2011

Скорее всего, вам придется использовать Dynamic SQL - запросить системные таблицы для всех таблиц, имеющих столбцы с именем EquipmentId, и построить динамический SQL-запрос, запрашивающий каждую таблицу на наличие именно того конкретного EquipmentId, который вам нужен. .

РЕДАКТИРОВАТЬ: @ mellamokb кажется гораздо проще - попробуйте.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...