CREATE TABLE test (id INT ,begindate DATE,enddate date) INSERT INTO test SELECT 1,'2012-11-21','2012-11-22' UNION ALL SELECT 1,'2012-11-23','2012-12-22' UNION ALL SELECT 1,'2012-12-23','2999-12-31' UNION ALL SELECT 2,'2012-11-21','2999-12-31' SELECT * FROM test
其实我的意思是想你的表设计成这样,不知道你看懂没 [其他解释] 单价表(单号,建立日期,客户,生效日,失效日) 单价明细表(单号,品名,单价) 这样会不会好点,查询当前单价 就找getdate between 生效日 and 失效日。 [其他解释]
if OBJECT_ID('单价表') is not null drop table 单价表 go create table 单价表 ( 单号 varchar(10), 建立日期 datetime, 客户 varchar(10) ) go insert 单价表 select '10001','2012-10-06 18:24:32','U001' union all select '10002','2012-10-14 09:32:53','U001' go
if OBJECT_ID('单价明细表')is not null drop table 单价明细表 go create table 单价明细表 ( 单号 varchar(10), 品名 varchar(10), 单价 numeric(8,2), 生效日 datetime, 失效日 datetime ) go insert 单价明细表 select '10001','test01',18.50,'2012-09-30','2012-10-07' union all select '10001','test02',19.50,'2012-10-30','2012-11-07' union all select '10002','test01',25.50,'2012-11-08','2012-11-30' union all select '10002','test02',18.50,'2012-12-01','2012-12-05' union all select '10001','test01',24.50,'2012-12-06','2012-12-31' go
select a.*, b.单价, b.生效日, b.失效日 from 单价表 a inner join 单价明细表 b on a.单号=b.单号 where a.建立日期 between b.生效日 and b.失效日 /* 单号建立日期客户单价生效日失效日 100012012-10-06 18:24:32.000U00118.502012-09-30 00:00:00.0002012-10-07 00:00:00.000 */
我觉得没什么问题
------其他解决方案--------------------
为什么不弄个触发器呢,把每次修改新增的数据时把数据插入到另一个表,这样可以确保主表都是唯一性。而且查看历史记录也很方便啊。 [其他解释] 我想确认这种单价表 sql表设计方式 是否正确,请问各位单价表都是怎么设计的? [其他解释] 你这个设计是可以的,只需要传入需要查询的日期,然后between 生效日 and 失效日就可以了。但是注意几点: 1、每个单价的最后一条数据的失效日期最好硬性写定一个值,如2999-12-31。即永不过期,这样在以后使用的时候很有好处。 2、如果你的日期只精确到天数,那么切记同一个单价,多条数据的失效日要在下一条数据的生效日前一天。不然between and 的时候会有重复数据 [其他解释]
--生效日不为空 select a.客户, b.品名, b.单价, b.生效日 from 单价表 as a inner join 单价明细表 as b on a.单号 = b.单号 where 生效日 <= getdate() and 生效日+1 >= getdate() union all --生效日为空 select a.客户, b.品名, b.单价, b.生效日 from 单价表 as a inner join 单价明细表 as b on a.单号 = b.单号 where b.生效日 is null and 生效日 = ( select max(生效日) from 单价表 as t1 inner join 单价名表 as t2 on t1.单号 = t2.单号 where t1.客户 = a.客户 and t2.品名 = b.品名 )
--生效日不为空 select a.客户, b.品名, b.单价, b.生效日 from 单价表 as a inner join 单价明细表 as b on a.单号 = b.单号 where 生效日 <= getdate() and 生效日+1 >= getdate() union all --生效日为空 select a.客户, b.品名, b.单价, b.生效日 from 单价表 as a inner join 单价明细表 as b on a.单号 = b.单号 where b.生效日 is null and 失效日 = ( select max(生效日) from 单价表 as t1 inner join 单价名表 as t2 on t1.单号 = t2.单号 where t1.客户 = a.客户 and t2.品名 = b.品名 )
--生效日不为空 select a.客户, b.品名, b.单价, b.生效日 from 单价表 as a inner join 单价明细表 as b on a.单号 = b.单号 where 生效日 <= getdate() and 生效日+1 >= getdate() union all --生效日为空 select a.客户, b.品名, b.单价, b.生效日 from 单价表 as a inner join 单价明细表 as b on a.单号 = b.单号 where b.失效日 is null and 生效日 = ( select max(生效日) from 单价表 as t1 inner join 单价名表 as t2 on t1.单号 = t2.单号 where t1.客户 = a.客户 and t2.品名 = b.品名 )
[其他解释]
您的意思是我这个代码效率太差是吗?
select a.客户, b.品名, b.单价, b.生效日 from 单价表 as a inner join 单价明细表 as b on a.单号 = b.单号 where b.生效日 is null and 失效日 = ( select max(生效日) from 单价表 as t1 inner join 单价名表 as t2 on t1.单号 = t2.单号 where t1.客户 = a.客户 and t2.品名 = b.品名 )
--生效日不为空 select a.客户, b.品名, b.单价, b.生效日 from 单价表 as a inner join 单价明细表 as b on a.单号 = b.单号 where 生效日 <= getdate() and 生效日+1 >= getdate() union all --生效日为空 select a.客户, b.品名, b.单价, b.生效日 from 单价表 as a inner join 单价明细表 as b on a.单号 = b.单号 where b.失效日 is null and 生效日 = ( select max(生效日) from 单价表 as t1 inner join 单价名表 as t2 on t1.单号 = t2.单号 where t1.客户 = a.客户 and t2.品名 = b.品名 )
[其他解释]
而且生效日有可能有多个,用=号会报错
select a.客户, b.品名, b.单价, b.生效日 from 单价表 as a inner join 单价明细表 as b on a.单号 = b.单号
where b.失效日 is null and 生效日 = ( select max(生效日) from 单价表 as t1 inner join 单价名表 as t2 on t1.单号 = t2.单号 where t1.客户 = a.客户 and t2.品名 = b.品名 ) 同一个产品怎么会有多个生效日呢? 我取得是最大值啊!
if exists(select 1 from inserted) and not exists(select 1 from deleted) --insert update 单价明细表 set 失效日 = t.生效日 - 1 from 单价表 a join 单价明细表 b on a.单号 = b.单号 join (select t1.客户, t2.品名, t2.生效日, t2.单号 from 单价表 t1 join inserted t2 on t1.单号 = t2.单号) t on a.客户 = t.客户 and b.品名 = t.品名 where a.单号 <> t.单号 and 失效日 is null