我在SQL Server 2005中有以下表格
ReceiptPoint: ID (PK), Name
GasIndexLocation: Location (PK)
ReceiptPointIndexLocation: ReceiptPointId (FK), IndexLocation (FK), StartDate, EndDate
在任何一天,ReceiptPoint都可以映射到一个或多个IndexLocations。我需要能够在某一天看到与IndexLocations进行比较的内容。对于具有多个IndexLocations的ReceiptPoint,它应显示为某种分隔列表(用于向用户显示)。
我有两个问题。
1)ReceiptPointIndexLocation目前没有主键。处理此问题的最佳方法是在表上添加递增索引字段吗?
2)如何获取给定日期使用的IndexLocations列表?据我所知,它需要使用不存在的字符串连接聚合函数。
我应该采用完全不同的方式来组织数据吗?这仍处于开发阶段,所以我愿意改变它。
答案 0 :(得分:1)
1)ReceiptPointIndexLocation的主键应该是全部四列。但是,这不会停止具有相同位置和收据的重叠日期的条目。当您可以使用复合键识别行时,不需要标识列。
2)SQL:
SELECT (SELECT t.indexlocation + ','
FROM RECEIPTPOINTINDEXLOCATION t
WHERE t.startdate >= @start
AND t.enddate <= @end
FOR XML PATH(''))
答案 1 :(得分:1)
有几种方法可以在SQL中聚合字符串。您应该阅读这篇文章Concatenating Row Values in Transact-SQL。最有效的方法是使用FOR XML PATH(',')技巧。
答案 2 :(得分:0)
我建议在表中添加一个递增索引以用作主键。如果您不这样做,我认为SQL Server会在幕后自动执行此操作,但我强烈建议您明确定义该列。这样,您可以通过主键引用各个行,而不必搜索两个交叉引用值。
另外,观察交叉引用表上的聚类。如果添加索引主键,请不要在索引主键上进行群集。您可能希望在两个外键上进行聚类,但您可以选择更有意义的外键。例如:
ALTER TABLE ReceiptPointIndexLocation ADD CONSTRAINT UK_ReceiptPointIndexLocation_ReceiptPointId_IndexLocation UNIQUE CLUSTERED (ReceiptPointId, IndexLocation)
或者,如果(ReceiptPointId,IndexLocation)的组合足够独特,您可以将其作为主键。