我有一个大约+100表的数据库,就像一半表有A列和A列一样。 B栏。
我的问题是,我是否可以查询具有特定值的列的所有表格,例如
SELECT * FROM DATABASE
在哪里
EACHTABLE HAS COLUMN A = 21 //只有表格有列然后是值
和
栏目B = 13
我不确定我会做得多么准确,谷歌也没有任何内容
答案 0 :(得分:2)
如果你肆无忌惮地生活,你可以使用未记录的MS存储过程sp_MSforeachtable
:
create table T1 (
ColumnA int not null,
ColumnB int not null
)
go
create table T2 (
ColumnA int not null,
Column2 int not null
)
go
create table T3 (
Column1 int not null,
ColumnB int not null
)
go
create table T4 (
ColumnA int not null,
ColumnB int not null
)
go
insert into T1 values (1,2);
insert into T2 values (3,4);
insert into T3 values (5,6);
insert into T4 values (7,8);
go
create table #Results (TableName sysname,ColumnA int,ColumnB int)
exec sp_MSforeachtable 'insert into #Results select ''?'',ColumnA,ColumnB from ?',
@whereand = ' and syso.object_id in (select object_id from sys.columns where name=''ColumnA'') and syso.object_id in (select object_id from sys.columns where name=''ColumnB'')'
select * from #Results
drop table #Results
结果:
TableName ColumnA ColumnB
------------------------------------- ----------- -----------
[dbo].[T1] 1 2
[dbo].[T4] 7 8
默认情况下,顾名思义,sp_MSforeachtable
将为数据库中的每个表执行相同的任务。但是,此过程的一个可选参数(称为@Whereand
)可用于修改枚举数据库中表的内部查询的WHERE
子句。有助于知道此内部查询已经为某些系统视图建立了两个别名。 o
是sysobjects
(旧系统视图)的别名。 syso
是sys.all_objects
的别名(更现代的系统视图)。
一旦sp_MSforeachtable
决定运行哪些表,它将执行作为其第一个参数给出的查询。但是,它会用模式和表名替换?
(?
是默认的替换字符。可以根据需要进行更改)
在这种情况下,我选择创建临时表,然后让每个选定的表将其结果存储到此临时表中,并在sp_MSforeachtable
运行完毕后,选择合并后的结果而不进行进一步处理。
有一个名为sp_MSforeachdb
的类似(并且类似的未记录的)过程将访问服务器上的每个用户数据库。这些甚至可以组合在一起(尽管你必须要小心两次加倍'
引号字符。但是,没有等效的sp_MSforeachcolumn
。
答案 1 :(得分:1)
试试这个:
select t.name from sys.objects t inner join sys.columns c
on t.name=OBJECT_NAME(c.object_id)
where t.type='U'
and c.name in('col1','col2')
group by t.name
having COUNT(*) = 2
order by 1
然后,您只需遍历所有表格并精确这些列的值。
像
Declare @out TABLE(tblname varchar(100))
if exists(select * from tbl1 where col1='21' and col2='22')
BEGIN
INSERT INTO @out
select tbl1
END
答案 2 :(得分:0)
您可以尝试使用动态查询。
select 'select * from '+table_name+ ' where'+column_name+'=21'
from information_schema.columns where column_name = 'A'
答案 3 :(得分:0)
我建议使用两个步骤: 首先,找出数据库中包含这两列的所有表,并将其用于临时派生表。因为我不是SQL-Server 2008的专家,所以我建议您查看白页。
表达式可能如下所示:
SELECT tablename
FROM information_schema.tables sdbt
WHERE "column a" IN
(SELECT columns
FROM information_schema.columns col
WHERE col.tablename = sdbt.tablename)
其次,使用表达式根据您的要求值过滤结果。
答案 4 :(得分:0)
这个命令应该一气呵成,只针对A列,相应修改以包含您需要的任何其他列:
exec sp_MSforeachtable
@command1=N'SELECT * FROM ? WHERE A = 21',
@whereand=' and o.name IN (SELECT TABLE_NAME FROM INFORMATION_SCHEMA.COLUMNS WHERE COLUMN_NAME = ''A'') '