SqlDataAdapter.FillSchema方法执行存储过程返回的DataSet,有问题!

madStone_l 2011-08-09 02:58:08
小弟,有几个存储过程,返回的数据集是一个DataSet包含两个DataTable,
其中存储过程里面都用到了临时表。

因为业务的需要,我必须得到第一个DataTable的表结构(就是存储过程中临时表的表结构),
如字段的类型、是否可空、最主要的是要获取字段的MaxLength属性。

然后我的数据访问代码如下:

using (SqlConnection connection = new SqlConnection(connectionString))
{
DataSet ds = new DataSet();
try
{
connection.Open();
SqlDataAdapter command = new SqlDataAdapter(SQLString, connection);
command.FillSchema(ds, SchemaType.Source);
}
catch (System.Data.SqlClient.SqlException ex)
{
throw new Exception(ex.Message);
}
return ds;
}

执行了出现异常,提示存储过程中的“#Temp”(临时表的名称)无效。
我用SQL Server Profiler跟踪得到的执行语句是:

SET FMTONLY OFF ;
SET NO_BROWSETABLE ON ;
SET FMTONLY ON ;
EXEC SearchOrder @start = N'0', @limit = N'100', @OrderNo = NULL,
@Mobele = NULL, @CustomerName = NULL, @OrderBeginDate = N'2011-08-01',
@OrderEndDate = N'2011-08-09', @OrderTypeID = NULL, @OrderStatusID = NULL,
@DrBusStationCode = NULL
SET FMTONLY OFF ;
SET NO_BROWSETABLE OFF ;

我存储过程写法绝对没有问题,因为我单独执行“EXEC SearchOrder @start = N'0', @limit = N'100',......”是可以正常返回数据的。

现在请高手支招,这是神马情况?
或者我怎么才能得到存储过程中临时表的表结构。
...全文
505 17 打赏 收藏 转发到动态 举报
写回复
用AI写文章
17 条回复
切换为时间正序
请发表友善的回复…
发表回复
WoErGongGuan 2013-01-15
  • 打赏
  • 举报
回复
引用 16 楼 ttjacky 的回复:
这个是因为临时表的机制引起的, 用select into #temp 生成的临时表只在当前连接有效, 你调用了以后,连接就断开了,临时表就不能在外面访问到了,所以会提示 临时表名称无效。
上线找你有事!
ttjacky 2013-01-06
  • 打赏
  • 举报
回复
这个是因为临时表的机制引起的, 用select into #temp 生成的临时表只在当前连接有效, 你调用了以后,连接就断开了,临时表就不能在外面访问到了,所以会提示 临时表名称无效。
madStone_l 2011-08-28
  • 打赏
  • 举报
回复
咳,还是没有解决
xiaod_xx 2011-08-24
  • 打赏
  • 举报
回复
帮顶,学习中。
随枫而来 2011-08-23
  • 打赏
  • 举报
回复
帮顶!!!!
madStone_l 2011-08-23
  • 打赏
  • 举报
回复
顶呀,帖子都沉海底了。
madStone_l 2011-08-15
  • 打赏
  • 举报
回复
帖子沉了~!!!!!
madStone_l 2011-08-12
  • 打赏
  • 举报
回复
[Quote=引用 6 楼 feiban55555 的回复:]

存储过程应该没有问题,关键你做临时表的时候怎么做,是不是给他表结构了,比如你用select into 临时表 from 实体表 ,然后在select 临时表的话 ,这样是没有问题的,因为你给了他一个让前台理解的表结构,但是你直接insert into一张临时表的话,因为没有表结构所以前台根本不知道你传了个什么对象,
[/Quote]
兄弟,不行。
我刚试了,先创建临时表,也不行。
小心眼 2011-08-09
  • 打赏
  • 举报
回复
Create PROC P_TEST1
@Name VARCHAR(20),
@Rowcount INT OUTPUT
AS
BEGIN
SELECT * into #tmp FROM dbo.Table_1
select * from #tmp
END
GO

这句话没有问题,如果存储过程是这样的话就会有问题了

Create PROC P_TEST1
@Name VARCHAR(20),
@Rowcount INT OUTPUT
AS
BEGIN
insert into #tmp
SELECT * FROM dbo.Table_1
select * from #tmp
END
GO

其实就是我上面说的问题
hjm1980_2011 2011-08-09
  • 打赏
  • 举报
回复
问题出现在临时表中

第一、临时表很大的可能是没有创建,如果真的创建成功,通过查询分析器可以查到数据,你可以设定创建临时表的断点,创建完以后,不要立即调用,也不要中断程序,这个时候通过查询分析器,查一下有没有这个表。

第二、要不取临时表的方法或语句不对,具体怎么取,网上搜索一下就会出来
小心眼 2011-08-09
  • 打赏
  • 举报
回复
存储过程应该有问题
小心眼 2011-08-09
  • 打赏
  • 举报
回复
存储过程应该没有问题,关键你做临时表的时候怎么做,是不是给他表结构了,比如你用select into 临时表 from 实体表 ,然后在select 临时表的话 ,这样是没有问题的,因为你给了他一个让前台理解的表结构,但是你直接insert into一张临时表的话,因为没有表结构所以前台根本不知道你传了个什么对象,
阿非 2011-08-09
  • 打赏
  • 举报
回复
定义成全局临时表试试
madStone_l 2011-08-09
  • 打赏
  • 举报
回复
[Quote=引用 2 楼 lmaohuanl 的回复:]

你的临时表都没有查出来怎么拿到?
[/Quote]
现在问题就是用SqlDataAdapter.FillSchema执行时,出现数据库错误,提示对象名 '#Temp' 无效。
用SqlDataAdapter.Fill就能正常执行,并返回DataSet,但是DataTable中的DataColumn.MaxLength属性全是-1。
就是请问高手怎么解决这个问题。。。。
madStone_l 2011-08-09
  • 打赏
  • 举报
回复
[Quote=引用 1 楼 gefangliang 的回复:]

一般的存储过程只在.dbml文件的设计视图中拖入即可,系统自动会形成方法。

Linq的存储过程返回的结果集如果不是实际存在的表(比如:临时表),没法生成模型类,就没法返回结果集了,这类存储过程生成的方法的结果集一般都是int类型。

有时候我们需要在存储过程里面写临时表,且将关联的若干张表的数据更新到临时表中来取数据,

而不使用视图或者左联右联,这样会提高查询的效率。


……
[/Quote]
大哥,我这不是Linq,项目中也没有.dbml文件。这都是C#写的数据访问代码……
最新进展,我用:
command.FillSchema(ds, SchemaType.Mapped);
仍然提示:对象名 '#Temp' 无效。
恳请高手支招呀
LMAOhuaNL 2011-08-09
  • 打赏
  • 举报
回复
你的临时表都没有查出来怎么拿到?
心灵彩虹 2011-08-09
  • 打赏
  • 举报
回复
一般的存储过程只在.dbml文件的设计视图中拖入即可,系统自动会形成方法。

Linq的存储过程返回的结果集如果不是实际存在的表(比如:临时表),没法生成模型类,就没法返回结果集了,这类存储过程生成的方法的结果集一般都是int类型。

有时候我们需要在存储过程里面写临时表,且将关联的若干张表的数据更新到临时表中来取数据,

而不使用视图或者左联右联,这样会提高查询的效率。



解决方法:


1、在数据库里创建一张表,结构要和临时表的列一致,比如叫T1;

2、把存储过程内容注释掉,改成简单的select * from T1;
3、把存储过程拖入设计器,编译。

4、修改存储过程为原来的代码,删掉T1表

110,533

社区成员

发帖
与我相关
我的任务
社区描述
.NET技术 C#
社区管理员
  • C#
  • Web++
  • by_封爱
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

让您成为最强悍的C#开发者

试试用AI创作助手写篇文章吧