【SQL】小心字符串拼接导致长度爆表
请看代码:
DECLARE @max VARCHAR(max)
SET @max='aaa...' --这里有8000个a
+'bb' --连接一个varchar常量或变量 SELECT LEN(@max)
别想当然以为它会返回8002,而是8000,select @max也只会得到8000个a,后面两个b没了。我们知道,varchar(max)类型不受字符数限制,但为什么会这样?
这其实与@max的数据类型无关,而是与字符串拼接后得到的数据类型有关,或者说,与字符串常量的数据类型推断有关。在SQL 2005和SQL 2008(R2)中,敲一个'a',系统会把它作为varchar(1),'aa'则是varchar(2),N'a'则是nvarchar(1),而'a...'(超过8000个a)呢,05中会当它是text,08则当它是varchar(max),常量或变量的数据类型可以通过系统函数SQL_VARIANT_PROPERTY获取,使用示例:
SELECT SQL_VARIANT_PROPERTY('a','BaseType')
有关该函数的更多信息请参看SSMS帮助或http://technet.microsoft.com/zh-cn/library/ms178550(v=sql.105).aspx
那么问题来了,既然超过8000个字符的常量系统会自动识别为大数据类型,不会出现截断,为什么拼接一下就歇菜了,这是因为varchar(n)+varchar(n)还是=varchar(n),拼接时系统会自动拓展数据长度,但不会更改数据类型(varchar(n)与varchar(max)应视为不同数据类型),又因为varchar(n)中的n最大取值为8000,所以varchar(x)+varchar(y)最大只会得到varchar(8000),当x+y>8000时,便会出现截断。
回到文章开头的例子,就很明了了,'aaa...'和'bb'都是varchar(n),拼接后得到varchar(8000),也就是截断了的8000个'aaa...',所以即便把它赋值给varchar(max)也无济于事。如果'aaa...'再多个a,情况又不同了,这时就是text或varchar(max)+varchar(n),对于05,会报text与varchar不能拼接,对于08,会正确得到无截断的'aaa...bb',因为varchar(max)+varchar(n)=varchar(max)。
OK就到这里,希望猿友在拼接SQL字串时留意这个问题。
【SQL】小心字符串拼接导致长度爆表的更多相关文章
- SQL Server 字符串拼接、读取
一.查询结果使用,字符串拼接 declare @names nvarchar(1000) declare @ParmDefinition nvarchar(1000) declare @sqltext ...
- SQL中字符串拼接
1. 概述 在SQL语句中经常需要进行字符串拼接,以sqlserver,oracle,mysql三种数据库为例,因为这三种数据库具有代表性. sqlserver: select '123'+'456' ...
- python 防止sql注入字符串拼接的正确用法
在使用pymysql模块时,在使用字符串拼接的注意事项错误用法1 sql='select * from where id="%d" and name="%s" ...
- sqlserver 字符串拼接及拆开联表查询的问题
一.sql根据一个以逗号隔开的人员guid类型的ID字符串查出其对应的姓名同样拼接成逗号隔开的字符串: 1.需求:管理员发送通知(通知分为普通通知,奖品订单,调查问卷三种类型)给用户,并且可以查看统计 ...
- Delphi SQL语句字符串拼接
单引号必须成对出现,最外层的单引号表示其内部符号为字符:除最外层以外的单引号,每两个单引号代表一个'字符.加号:+用于字符串之间的连接.字符串常量用四个单引号,例如 ' select * from T ...
- SQL Server 字符串拼接与拆分 string varchar Split and Join
1.Split SQL Server 2008 新语法: DECLARE @str VARCHAR(MAX) SET @str = REPLACE(@teeIDs, ',', '''),(''' ...
- SQL Where 字符串拼接
) set @s='1,2,3' --法一: --法二: exec('select * from tb where id in ('+@s+')')
- linux环境java程序cpu爆表问题查证
1.top命令查找导致cup爆表的进程 2. top -H -p10832 (10832是Java进程的PID)命令找出了具体的线程 3.使用用命令 jstack 10832> jstack.t ...
- 解决存储过程中拼接的SQL字符串超长导致sql语句被截取的问题
今天遇到了一个奇葩的问题:存储过程中的sql字符串拼接的太长,超出了分页存储过程执行sql参数的nvarchar(4000)的长度. 没办法,只能修改自己的存储过程,因为分页存储过程是不能动的. 开始 ...
随机推荐
- channel vs mutex
记录许总演讲PPT指出的实践: channel– 本质上是一个 MessageQueue– 非常正统的执行体间通讯设施• sync.Mutex/RWMutex/Cond/etc– 不要把 channe ...
- Ubuntu下安装 jdk6
Ubuntu下安装 jdk6 罗朝辉 (http://www.cnblogs.com/kesalin/) 本文遵循“署名-非商业用途-保持一致”创作公用协议 1,下载最新的 jdk6 版本,目前最 ...
- js模版引擎handlebars.js实用教程——如何引入Handlebars.js
返回目录 Jquery插件,第一步当然要引用Jquery啦,然后引用Handlebars.js即可,仅仅需要这两个js文件. <script type="text/javascript ...
- MVVM架构~knockoutjs系列之扩展ajax验证~验证数据是否存在
返回目录 在大部分网站里,用户名都是唯一的,即当用户注册时,如果用户输入的名字不合法,我们需要提示用户,让用户再起个新名字,而这种复杂的验证一般是通过JS来实现的,如果把它集成到ko里,那就完美了.有 ...
- Atitit 五种IO模型attilax总结 blocking和non-blocking synchronous IO和asynchronous I
Atitit 五种IO模型attilax总结 blocking和non-blocking synchronous IO和asynchronous I 1.1. .3 进程的阻塞1 1.2. 网络 ...
- NPM安装之后CMD中不能使用
NPM安装之后CMD中不能使用 这个情况就是path环境变量没有添加NPM 添加环境变量并重启CMD C:\Users\Mark\AppData\Roaming\npm\ 看看这个文件夹就知道为什么要 ...
- ssh(sturts2_spring_hibernate) 框架搭建之JPA代替hibernate
一.JPA用来替代hibernate ⒈JPA的全称是JAVA Persistence API.指的是JPA通过注解或者是XML描述对象—关系表的映射关系,并且将运行的实体对象持久化数据库中. ⒉JP ...
- 让BI告诉你:圣诞老人去哪了?
刚看到一篇关于圣诞节BI分析的文章,觉得很有意思,特来翻译了下和大家一起分享(可惜的是文章发布的时间有点久). 伴随着圣诞节即将到来的日子,POWER BI团队来回答大家最为关注的一个问题:圣诞老人到 ...
- php的几种运行模式CLI、CGI、FastCGI、mod_php
1.CLI:就是命令行,例如可以在控制台或者是shell中键入命令: php -f index.php 然后获取输出 2.CGI:以下是不同的说法与理解 公共网关接口”(Common Gateway ...
- backbone库学习-Collection
backbone库的结构: http://www.cnblogs.com/nuysoft/archive/2012/03/19/2404274.html 本文所有例子来自于http://blog.cs ...