测试1--准备数据
select top 10 * into #t from sysobjects
alter table #t add IDTEST int identity(1,1)   --加上ID列
select * from #t                              --执行正常
select IDTEST from #t                         --执行正常测试一完全正常,下面看测试2--准备工作
select top 10 * into #t from sysobjects
Create proc sp_test
as
begin
alter table #t add IDTEST int identity(1,1)
select * from #t                          --这行能正常输出IDTEST
select IDTEST from #t                     --若把此行注释,则上一句能正常查询也IDTEST列
drop table #t
end
--执行
exec sp_test消息 207,级别 16,状态 1,过程 sp_test,第 6 行
列名 'IDTEST' 无效。为啥在存储过程中用*号可以查询出IDTEST列,而无法指定IDTEST列查询呢?

解决方案 »

  1.   

    而当把Alter语句放在存储过程外,再执行此过程,又完成正常。
      

  2.   


    --准备工作
    select top 10 * into #t from sysobjects
    Create proc sp_test
    as
        begin
            select * from #t
            alter table #t add IDTEST int identity(1,1)
            select * from #t                   --这行能正常输出IDTEST,是的. 因为他调用过程的时候创建了IDTEST列,
           --select IDTEST from #t             
           --这里为什么就报错,因为我们创建过程的时候 idtest这个列还没有创建.这里做查询肯定报错! 意识也就是根本这个过程就创建不成功!
           --因为什么,因为这个查询有问题..#t里根本就没有这个idtest列..
           --为什么没有,因为过程还没有被执行..执行了就有了..但是创建都创建不了何来执行!对吧
            drop table #t    
            --如果你的表创建在过程内,这句完全没有比要.为什么没有必要,因为过程内创建的临时表只对自己可见.
            --执行完了过程临时表就 被 咔嚓掉了..意识也就是没有了..释放掉了..不占空间了.再也找不到这个临时表了,我相信你理解了
            --但是你把临时表创建在过程的外部..我相信也不一定好..当你的session 已释放掉..一断开.或你的服务已重启..你的temp就没有啦
            --那么你这个过程就瓦塔拉..因为他会抛出异常说找不到#t 这个表! 
        end
    --执行
    exec sp_test   --如果执行了过程!再做查询
    select IDTEST from #t  --这里应该就不会报错..为什么不报错,因为他已经执行了过程.创建了这个列! 
    --这样吧? 我语言组织能力烂得一逼! 我能不能引用书上的例子给你看一遍! 
    CREATE PROC proc2
    AS
    CREATE TABLE #t1      --这里在创建一个和上面完全一样的临时表.
    INSERT INTO #t1 VALUES (2) 
    SELECT * FROM #t1
    goCREATE PROC proc1
    AS
    begin
    CREATE TABLE #t1(co1 INT NOT NULL)
    INSERT INTO #t1 VALUES(1);
    SELECT * FROM #t1
    EXEC dbo.proc2;    --这里某写错,,过程在下面
    END--执行
    EXEC proc1--下面是你期望的结果
    col1
    1
    col1
    2--修改过程2
    ALTER PROC proc2
    AS
    CREATE TABLE #t1(col1 INT NULL,col2 INT NOT NULL)
    INSERT INTO #t1 VALUES(2,2)
    SELECT * FROM #t1
    go--在执行过程proc1
    EXEC PROC1col1
    1
    --
    --报错啦..为什么报错..因为 proc2 是创建了..但你你没有执行啊..
    --你没有执行那#t1 插俩数那肯定插不进
    --单独执行 proc 2
    EXEC dbo.proc2
    col1   col2
    1       2
    --没有问题...那这个#t1 已经创建啦
    --那么我再执行proc1
    --完全没有问题啊
    EXEC proc1
    col1
    1
    col1   col2
    1       2/*========================
    我一sql新人,不对请拍砖我改!
    不过很多东西别把自己绕进去!
    不懂就一直看..看到懂为止!
    语言组织能力差得很...给你直接上书上的例子..
    希望对你有帮助!
    ==========================*/
      

  3.   

    好久不见,
    首先 #t 是对 会话的 全局变量,你这样是写在 proc 中, 在外调多次至少也是错的,至少 不是好的方式。