今天在测试分布式数据库访问时,遇到异常:OracleParameter已在对象集合中,刚开始的时候还以为是重复添加的问题,经过多方测试还是有问题,后来将传入的参数克隆一份赋给命令参数,问题解决.后面觉得很奇怪,就去网上查了下,好像是这些参数对象不能同时添加到多个命令中,具体机制就不得而知了.但一个参数对象被添加到多个命令中,实际上都是指向同一份,对象还是同一个,如果ADO在底层会修改命令参数(返回值参数肯定得修改),那么不允许一个参数对象添加到多个命令中就很容易理解了.因为那样会造成混乱.
private void PrepareCommand(OracleCommand Command,OracleParameter[] Parameters,OracleTransaction Trans) { try { Command.Parameters.Clear(); if (Parameters != null) { foreach (var p in Parameters) { //这是正确安全的写法 OracleParameter theP = ((ICloneable)p).Clone() as OracleParameter; Command.Parameters.Add(theP); //Command.Parameters.Add(p); //这是不安全的写法. } } if (Trans != null) { Command.Transaction = Trans; } } catch { } }
上面的try,catch在实际中应该除掉,我写这个是为了抓虫子!
其实我无意中发现解决之道,是因为我的是多线程,我的想法是尽量将变量独立开,不共享,所以无意走对了路.
PS:学习在出错中进步,有出错才有未来!
补充:想起来了,其实这种规则在Silverlight将实体数据从服务器获取后,也不能加入到其它集合的.
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 [email protected] 举报,一经查实,本站将立刻删除。