declare @StartIP int
set @StartIP=(0x7FFFFFFF+1)
print @StartIP这段代码执行提示溢出消息 8115,级别 16,状态 2,第 3 行
将 expression 转换为数据类型 int 时出现算术溢出错误。
declare @StartIP bigint
set @StartIP=(0x7FFFFFFFFFFFFFFF+1)
print @StartIP为啥下面这段就不提示溢出呢?

解决方案 »

  1.   

    set @StartIP=(0x7FFFFFFFFFFFFFFF+1)你这个转过来超过INT所能表示的最大数了
      

  2.   

    declare @StartIP int 
    set @StartIP=(0x7FFFFFFF+1) 
    print @StartIP 
    二进制数据转换成int超过int的范围了  而没有超出bigint的范围
      

  3.   

    SELECT CONVERT(INT,0x7FFFFFFF),CONVERT(INT,0x7FFFFFFFFFFFFFFF)
    --2147483647 -1
      

  4.   

    第二个其实是超出了bigint的最大正整数范围了的 
      

  5.   

    int 的范围
     -2^31 (-2,147,483,648) 到 2^31-1 (2,147,483,647)这下明白了吧
     
      

  6.   

    .net里面ulong ee = 0x7FFFFFFFFFFFFFFF+1;这样编译的时候会有益处提示的
      

  7.   

    ulong类型
    0~18 446,744,073,709,551,615
    bigint
    -2^63 (-9,223,372,036,854,775,808) 至 2^63-1 (9,223,372,036,854,775,807)int
    -2^31 (-2,147,483,648) 到2^31 - 1 (2,147,483,647)SELECT CONVERT(INT,0x7FFFFFFF),CONVERT(INT,0x7FFFFFFFFFFFFFFF)
                
    ----------- -----------
    2147483647  -1(1 行受影响)
    至于ulong ee = 0x7FFFFFFFFFFFFFFF+1会报溢出应该是由于0x7FFFFFFFFFFFFFFF是-1的原因
      

  8.   

    那为啥 sql语句 bigint的时候不会报错呢,
    declare @StartIP bigint 
    set @StartIP=(0x7FFFFFFFFFFFFFFF+1) 
    @StartIP的值就直接为0了
      

  9.   

    declare @StartIP bigint
    set @StartIP=(0x7FFFFFFFFFFFFFFF+1) 
    >>>
    常量 0x7FFFFFFFFFFFFFFF非 big 类型, 具体是什么我不清楚, 所以加1後不会产生overflow.set @startIP= CAST(CAST(0x7FFFFFFFFFFFFFFF as BIGINT)+1 as BIGINT ) 
    这样便会出错了.
      

  10.   


    ulong类型不支持负值,而bigint支持
      

  11.   

    看来我理解有误,的确0x7FFFFFFFFFFFFFFF是bigint的最大值而SQL是转成int的-1然后+1变成0在转成bigint的,你可以看下@StartIP结果是0
      

  12.   

    具体来说还是二进制转的时候出问题了,具体转成什么,转了几次要问微软所以还是需要显式转换select cast(0x7FFFFFFFFFFFFFFF as bigint)+1
    --------------------
    消息 8115,级别 16,状态 2,第 1 行
    将 expression 转换为数据类型 bigint 时发生算术溢出错误。(1 行受影响)
      

  13.   

    这其实涉及到的是 sql数据类型的优先级问题declare @StartIP int 
    set @StartIP=(0x7FFFFFFF+1
    print @StartIP declare @StartIP bigint 
    set @StartIP=(0x7FFFFFFFFFFFFFFF+1
    print @StartIP 其关键是在 这个 1 上,sql 默认其是 int 型!
    所以两者相加,0x7FFFFFFF 和  0x7FFFFFFFFFFFFFFF 都 被默认转换成 int型select convert(int,0x7FFFFFFF)
    /*2147483647*/
    select convert(int,0x7FFFFFFFFFFFFFFF)
    /*-1*/前者+1后,超出Int的范围
    后者+1后,=0,不用Bigint都可以, 甚至你定义成smallint都可以。当然,再看一下,如果你把后者改一下
    declare @StartIP bigint
    set @StartIP=(0x7FFFFFFFFFFFFFFF+convert(bigint,1)) 
    print @StartIP 那么同样是会报溢出的错误的同样,如果把前者的+1指定为smallint,也就不会报错了
    declare @StartIP int 
    set @StartIP=(0x7FFFFFFF+convert(smallint,1)) 
    print @StartIP /* 0 */