删除数据时出错带来的一系列问题,望指点.

michael_monkey 2004-12-23 02:40:26
我有一ADP项目,数据库是SQL2000Server,其中有表:“操作者”,“每月系数”等。
ADP项目一窗体,数据源是:

SELECT 每月系数.* FROM 每月系数 INNER JOIN 操作者 ON 每月系数.操作者编号 = 操作者.操作者编号 WHERE (操作者.状态 = 1) ORDER BY 每月系数.月份

增加修改都没有问题,删除时候提示:“无法为更新定位行.一些值可能已在最后一次读取后已更改.”。



几番折腾,无解。于是新建一查询view1,语句同上,然后在查询分析器里面执行,看看是什么反应:

delete from view1 where 月份='200412'

执行不成功,提示:
服务器: 消息 4427,级别 16,状态 1,行 1
视图或函数 'view1' 不可更新,因为其定义中包含 TOP 子句。

我想明明我定义的view1中没有top子句呀,于是打开查看,果然有“TOP 100 PERCENT”,于是,删除,保存,但它总是自动加上“TOP 100 PERCENT”,郁闷。

望指点,不甚感激!
...全文
132 点赞 收藏 19
写回复
19 条回复
michael_monkey 2004年12月23日
意思是说我只能编写程序,直接操纵sql语句,实现功能了?
回复 点赞
ACCESS和SQL Server本来就是两种不同的构架,SQL语法也不完全相同(也可以说差异较大)
回复 点赞
michael_monkey 2004年12月23日
第二个问题很明白了

现在第一个问题,我转换了一个方式向你们提问:
现在的查询是:

SELECT 每月系数.* FROM 每月系数 INNER JOIN 操作者 ON 每月系数.操作者编号 = 操作者.操作者编号 WHERE (操作者.状态 = 1)

在查询分析器中执行:
delete from view1 where 月份='200412'

提示:
服务器: 消息 4405,级别 16,状态 1,行 1
视图或函数 'view1' 不可更新,因为修改会影响多个基表。



对于我来说,总算有点眉目了,这个查询不适合用于更新操作,可能在应用程序中能勉强执行,但是会出问题。

那象我上面所说的需要过滤的情况应该怎么办呢?

这个ADP项目是由MDB转化来的,在MDB中这个窗体的数据源是三个表(加上表“部门”)的联合查询,没有出现任何问题的,为什么到了SQL server以后就不行了呢?
回复 点赞
--在关联,也可以对基表删除啊

delete a
FROM 每月系数 a INNER JOIN 操作者 b ON a.操作者编号 = b.操作者编号
WHERE (b.状态 = 1) and a.月份='200412'
回复 点赞
vinsonshen 2004年12月23日
请参考以下联机帮助说明:

对于视图定义中的 SELECT 子句有几个限制。CREATE VIEW 语句不能:

包含 COMPUTE 或 COMPUTE BY 子句。


包含 ORDER BY 子句,除非在 SELECT 语句的选择列表中也有一个 TOP 子句。


包含 INTO 关键字。


引用临时表或表变量。
回复 点赞
michael_monkey 2004年12月23日
to zjcxc:

1、因为要对操作者进行过滤,所以要用查询
2、不带order by,仍然如此
回复 点赞
michael_monkey 2004年12月23日
第二个问题就算是饶了它

对于第一个问题有什么好办法?
根据上面的语句可以看出来,我主要是对表“每月系数”进行操作,但是要对离职人员进行过滤(操作者.状态 = 1),所以窗体的数据源必须是“每月系数”和“操作者”的一个联合查询(见楼顶)。

这个问题是增加修改都可以,就是删除的时候会提示:“无法为更新定位行.一些值可能已在最后一次读取后已更改.”。其实真正的数据已经删除了,只是会提示,而且窗体中仍然显示着这笔数据,下次打开时就没有了。

不可理解的是在查询分析器中执行“delete from view1 where 月份='200412'”又提示说是不可更新的,不可更新为什么又能删除呢?

服务器: 消息 4427,级别 16,状态 1,行 1
视图或函数 'v1' 不可更新,因为其定义中包含 TOP 子句。
回复 点赞
或者创建一不带 order by 的视图
回复 点赞
其实你直接从基表删除不行么?
回复 点赞
用order by 的视图,必须配合加上 top ,这是硬性的规定,没有办法的.
回复 点赞
michael_monkey 2004年12月23日
to chinaandys:

一样的效果,还是提示
回复 点赞
chinaandys 2004年12月23日
试一试这样:
select * from
(SELECT 每月系数.* FROM 每月系数 INNER JOIN 操作者 ON 每月系数.操作者编号 = 操作者.操作者编号
where 操作者.状态 = 1 ) a
order by 月份
回复 点赞
michael_monkey 2004年12月23日
to NinGoo:

服务器: 消息 1033,级别 15,状态 1,过程 v_test,行 3
除非同时指定了 TOP,否则 ORDER BY 子句在视图、内嵌函数、派生表和子查询中无效。
回复 点赞
michael_monkey 2004年12月23日
to chinaandys:

都有主键的

“每月系数”的主键是“自动编号”
“操作者”的主键是“操作者编号”
回复 点赞
chinaandys 2004年12月23日
//删除时候提示:“无法为更新定位行.一些值可能已在最后一次读取后已更改.”。

-----要新建一个主键


回复 点赞
NinGoo 2004年12月23日
你试下在查询分析器中建view看看

create view v_test
as
SELECT 每月系数.* FROM 每月系数 INNER JOIN 操作者 ON 每月系数.操作者编号 = 操作者.操作者编号 WHERE (操作者.状态 = 1) ORDER BY 每月系数.月份
回复 点赞
michael_monkey 2004年12月23日
现在发现一点门道,如果没有“ORDER BY 每月系数.月份”子句,它就不会自动加上“TOP 100 PERCENT”,有那个排序子句,肯定会自动加上top子句,好怪!
回复 点赞
michael_monkey 2004年12月23日
新建视图——点击SQL——粘贴“SELECT 每月系数.* FROM 每月系数 INNER JOIN 操作者 ON 每月系数.操作者编号 = 操作者.操作者编号 WHERE (操作者.状态 = 1) ORDER BY 每月系数.月份”

然后它就自动加上“TOP 100 PERCENT”
回复 点赞
NinGoo 2004年12月23日
总是自动加上“TOP 100 PERCENT”???

你的view是怎么建的?
回复 点赞
发动态
发帖子
应用实例
创建于2007-09-28

1.1w+

社区成员

6.8w+

社区内容

MS-SQL Server 应用实例
社区公告
暂无公告