在SQL Server中,有两种元数据模式:
我听说INFORMATION_SCHEMA
表基于ANSI标准。开发时,例如存储过程,在INFORMATION_SCHEMA
表上使用sys
表是否明智?
答案 0 :(得分:32)
除非您正在编写一个您知道的应用程序需要可移植的应用程序,或者您只需要非常基本的信息,否则我将默认使用专有的SQL Server系统视图开始。
Information_Schema
视图仅显示与SQL-92标准兼容的对象。这意味着即使是非常基本的结构(如索引)也没有信息模式视图(这些结构未在标准中定义,而是作为实现细节保留。)更不用说任何SQL Server专有功能。
此外,它可能不是人们可以假设的便携性的灵丹妙药。实现在系统之间仍然存在差异。 Oracle根本没有“开箱即用”地实现它,the MySql docs说:
SQL Server 2000的用户(也遵循该标准)可能会注意到 相似性很强。但是,MySQL省略了许多列 与我们的实现无关,并添加了列 MySQL特有。一个这样的列是中的ENGINE列 INFORMATION_SCHEMA.TABLES表。
即使对于面包和黄油SQL构造(例如外键约束),Information_Schema
视图的工作效率也明显低于sys.
视图,因为它们不会公开允许有效查询的对象ID
e.g。请参阅问题SQL query slow-down from 1 second to 11 minutes - why?和执行计划。
答案 1 :(得分:31)
我总是尝试使用Information_schema
视图直接查询sys
架构。
视图符合ISO标准,因此从理论上讲,您应该能够轻松地跨不同的RDBMS迁移任何查询。
但是,在某些情况下,我需要的信息在视图中不可用。
我提供了一些链接,其中包含有关视图和查询SQL Server目录的更多信息。
答案 2 :(得分:10)
INFORMATION_SCHEMA
更适合可能需要与各种数据库连接的外部代码。一旦开始编程在数据库中,可移植性就会消失。如果您正在编写存储过程,那就告诉我您已经致力于特定的数据库平台(无论好坏)。如果您已经提交到SQL Server,那么请务必使用sys
视图。
答案 3 :(得分:1)
我不会重复其他一些答案,而是添加一个性能视角。正如Martin Smith在他的回答中提到的那样,information_schema视图不是这种信息的最有效来源,因为它们必须暴露必须从多个底层源收集的标准列。从这个角度来看,sys视图可以更高效,所以如果你有高性能要求,而且不必担心可移植性,你可能应该使用sys视图。
例如,下面的第一个查询使用information_schema.tables来检查表是否存在。第二个使用sys.tables来做同样的事情。
if exists (select * from information_schema.tables where table_schema = 'dbo' and table_name = 'MyTable')
print '75% cost';
if exists (select * from sys.tables where object_id = object_id('dbo.MyTable'))
print '25% cost';
当您查看这些IO时,第一个查询对sysschobjs和sysclsobjs有4个逻辑读取,而第二个查询没有。此外,第一个执行两个非聚集索引搜索和一个键查找,而第二个只执行单个聚簇索引搜索。根据查询计划,第一个比第二个花费多3倍。如果您必须在大型系统中多次执行此操作(例如部署时间),则可能会增加并导致性能问题。但这实际上只适用于负载很重的系统。大多数IT业务系统都没有这些级别的性能问题。
同样,与大多数系统中的其他查询相比,它们的总体成本非常小,但如果您的系统有很多此类活动,则可能会增加。