Sql 引用表的群集与非群集

Sql 引用表的群集与非群集,sql,sql-server,tsql,indexing,clustered-index,Sql,Sql Server,Tsql,Indexing,Clustered Index,我有一个简单的产品表,用于跟踪产品数据。大多数时候我不需要知道它是什么类型的产品,但偶尔我需要产品类型。现在,因为不是所有产品都有一个类型(这会导致大量空行),所以当我需要该信息时,我使用一个引用表来连接产品类型。引用表使用复合键,我想弄清楚的是主键应该是聚集索引还是非聚集索引。product表的主键有一个聚集索引,因此我想知道如果联接也是聚集索引(以便id的顺序是有序的),它是否会更有效。或者在连接过程中忽略了这一点,因此非聚集的会更有效,因为它不执行密钥查找 CREATE TABLE [db

我有一个简单的产品表,用于跟踪产品数据。大多数时候我不需要知道它是什么类型的产品,但偶尔我需要产品类型。现在,因为不是所有产品都有一个类型(这会导致大量空行),所以当我需要该信息时,我使用一个引用表来连接产品类型。引用表使用复合键,我想弄清楚的是主键应该是聚集索引还是非聚集索引。product表的主键有一个聚集索引,因此我想知道如果联接也是聚集索引(以便id的顺序是有序的),它是否会更有效。或者在连接过程中忽略了这一点,因此非聚集的会更有效,因为它不执行密钥查找

CREATE TABLE [dbo].[sales_product_type]
(
    [FK_product_id] [int] NOT NULL,
    [product_type] [int] NOT NULL,
    [type_description] [nvarchar](max) NULL,

    CONSTRAINT [PK_sales_product_type] 
        PRIMARY KEY CLUSTERED ([FK_product_id] ASC, [product_type] 
) ON [PRIMARY]
GO

CREATE TABLE [dbo].[sales_product]
(
    [product_id] [int] IDENTITY(1,1) NOT NULL,
    [FK_store_id] [int] NOT NULL,
    [price] [int] NOT NULL,
    [product_name] [nvarchar](max) NOT NULL,
    [units] [int] NULL,

    CONSTRAINT [PK_sales_product] 
        PRIMARY KEY CLUSTERED ([product_id] ASC)
) ON [PRIMARY] TEXTIMAGE_ON [PRIMARY]
GO

如果在查询产品类型时需要
[type\u description]
列,则应使用聚集索引。原因是聚集索引将包含表的所有列(包括键列Product ID和Product Type)

另一方面,如果您在产品ID和产品类型上只有一个非聚集索引,那么当您的查询需要获取
Type\u description
时,它必须对结果数据集中的每个类型进行堆查找

因此,如果您需要在结果中输入描述,您应该保留一个聚集索引


但是,在您的特定场景中,
type\u description
是否大于8000个字符并不重要。如前所述(和),如果列的值超过8000个字符,则该列的值将存储在行外。因此,在任何情况下,引擎都必须执行查找以获取该值


如果您不打算经常查询
type\u description
,使用非聚集索引可能会导致更低的读取-因为引擎不必遍历
type\u description
字段。但在决定一种方法之前,我会测试这两种方法

通常,我总是在表上有一个聚集索引。如果需要,我可以添加一个非聚集索引来优化特定的查询