sql server数据库中char、nchar、varchar、nvarchar的选择

    在数据库中,字符型的数据是最多的,可以占到整个数据库的80%以上。为此正确处理字符型的数据,对于提高数据库的性能有很大的作用。

    在字符型数据中,用的最多的就是Char与Varchar两种类型。前面的是固定长度,而后面的是可变长度。

    现在我们需要考虑的是,在什么情况下使用Char字符型数据,什么情况下采用Varchar字符型数据。在这部分内容中,我就跟大家来探讨一下这个话题。

    VARCHAR数据类型可以节省存储空间,提高数据处理的效率。

首先说区别:

   char 类型:

      对英文字符占用1个字节,对一个汉字占用2个字节。

      char 存储定长数据很方便,char 字段上的索引效率极高。

      使用:

          比如定义 char(10),那么不论你存储的数据是否达到了10个字节,都要占去10个字节的空间,不够的字符用空格去填。

          因为是固定长度,所以速度效率高。

   nchar类型:

      对每个英文字符都占用2个字节,对一个汉字也占用两个字节,所有的字符都占用2个字节。(这是为了方便与其他多种字符进行转换,如中文,音标等)

   varchar(n):

      n 的值必须介于 1  与  8,000 之间。

   nvarchar(n) :

      n 的值必须介于 1  与  4,000 之间。

    varchar(100)/char(100)能存50个汉字,nvarchar(100)/nchar(100)能存100个汉字

    varchar 类型是可变的——如果 varchar (8) 你只存了一个字母,在内存中只占2个字节

    由于char是以固定长度的,所以它的速度会比varchar快得多!但程序处理起来要麻烦一点,要用trim之类的函数把两边的空格去掉!

区别:

  ①从存储方式上,nvarchar是按字符存储的,而 varchar是按字节存储的;

  ②从存储量上考虑, varchar比较节省空间,因为存储大小为字节的实际长度,而 nvarchar是双字节存储;

  ③在使用上,如果存储内容都是英文字符而没有汉字等其他语言符号,建议使用varchar;含有汉字的使用nvarchar,因为nvarchar是使用Unicode编码,即统一的字符编码标准,会减少乱码的出现几率;

  ④   如果你做的项目可能涉及不同语言之间的转换,建议用nvarchar。

(3)优缺点:

   Nvarchar优点:判断字符串的时候可以不需要考虑中英文两种字符的差别,可以避免程序中乱码的问题。

           缺点:存储英文字符会增大一倍的存储空间.但是在存储代价已经很低廉的情况下,优先考虑兼容性会给你带来更多好处的,效率没有varchar高。

(4)为什么要用nvarchar?

    有n前缀的,n表示Unicode字符,即所有字符都占两个字节,nchar,nvarchar

字符中,英文字符只需要一个字节存储就足够了,但汉字众多,需要两个字节存储,英文与汉字同时存在时容易造成混乱,Unicode字符集就是为了解决字符集这种不兼容的问题而产生的,它所有的字符都用两个字节表示,即英文字符也是用两个字节表示。

(5)有关var的简单介绍:

有var前缀的,表示是实际存储空间是变长的,varchar,nvarchar

所谓定长就是长度固定的,当输入的数据长度没有达到指定的长度时将自动以英文空格在其后面填充,使长度达到相应的长度;而变长字符数据则不会以空格填充,比较例外的是,text存储的也是可变长。

(6)如何使用这些类型?

    如果你肯定存储的数据长度,而且不包中文的,可以选择char类型。

    如果肯定存储的数据长度,但可能包括中文,可以选择nchar类型。

    如果不确定存储的数据长度,存储只有英文、数字的最好用varchar

    如果不确定存储的数据长度,也有可能有中文,可以选择nvarchar类型,在SQL Server2005中也是比较常用的字符数据类型。

  在字符长度一定时char的相关性能比varchar好,而在长度不确定时,char类型的字段在使用时性能略差。

  由于char是以固定长度的,所以它的速度会比 varchar快得多(这里说的很粗糙,增删改是哪个速度)!但程序处理起来要麻烦一点,要用trim之类的函数把两边的空格去掉!

  varchar比char节省空间,在效率上比char会稍微差一些,即要想获得效率,就必须牺牲一定的空间,这也就是我们在数据库设计上常说的‘以空间换效率’。

  varchar 虽然比char节省空间,但是如果一个varchar列经常被修改,而且每次被修改的数据的长度不同,这会引起‘行迁移’(Row Migration)现象,而这造成多余的I/O,是数据库设计和调整中要尽力避免的,在这种情况下用char代替varchar2效果会更好一些。

    <反复的修改,优化,整理的简洁、明了一些>

如何选择:

    我们知道VARCHAR数据类型是一把双刃剑,其在带来性能提升的同时,也可能会存在着一些额外的消耗。我们在评估到底是使用VARCHAR数据类型还是采用CHAR数据类型时,就需要进行均衡。在实际项目中,我们会考量如下情况。

    一是根据字符的长度来判断。如某个字段,像人的名字,其最长的长度也是有限的。如我们给其分配18个字符长度即可。此时虽然每个人的名字长度有可能不同,但是即使为其分配了固定长度的字符类型,即18个字符长度,最后浪费的空间也不是很大。而如果采用NVARCHAR数据类型时,万一以后需要改名,而原先的存储空间不足用来容纳新的值,反而会造成一些额外的工作。在这种情况下,进行均衡时,会认为采用CHAR固定长度的数据类型更好。在实际项目中,如果某个字段的字符长度比较短此时一般是采用固定字符长度。

    二是考虑其长度的是否相近。如果某个字段其长度虽然比较长,但是其长度总是近似的,如一般在90个到100个字符之间,甚至是相同的长度。此时比较适合采用CHAR字符类型。比较典型的应用就是MD5哈希值。当利用MD5哈希值来存储用户密码时,就非常使用采用CHAR字符类型。因为其长度是相同的。另外,像用来存储用户的身份证号码等等,一般也建议使用CHAR类型的数据。

    三是从碎片角度进行考虑。使用CHAR字符型时,由于存储空间都是一次性分配的。为此某个字段的内容,其都是存储在一起的。单从这个角度来讲,其不存在碎片的困扰。而可变长度的字符数据类型,其存储的长度是可变的。当其更改前后数据长度不一致时,就不可避免的会出现碎片的问题。故使用可变长度的字符型数据时,数据库管理员要时不时的对碎片进行整理。如执行数据库导出导入作业,来消除碎片。

    四是即使使用Varchar数据类型,也不能够太过于慷慨。这是什么意思呢?如现在用户需要存储一个地址信息。根据评估,只要使用100个字符就可以了。但是有些数据库管理员会认为,反正Varchar数据类型是根据实际的需要来分配长度的。还不如给其大一点的呢。为此他们可能会为这个字段一次性分配200个字符的存储空间。这VARCHAR(100)与VARCHAR(200)真的相同吗?结果是否定的。虽然他们用来存储90个字符的数据,其存储空间相同。但是对于内存的消耗是不同的。这对于排序或者临时表(这些内容都需要通过内存来实现)作业会产生比较大的不利影响。所以如果某些字段会涉及到文件排序或者基于磁盘的临时表时,分配VARCHAR数据类型时仍然不能够太过于慷慨。还是要评估实际需要的长度,然后选择一个最长的字段来设置字符长度。如果为了考虑冗余,可以留10%左右的字符长度。千万不能认为其为根据实际长度来分配存储空间,而随意的分配长度,或者说干脆使用最大的字符长度。

char与varchar的比较:

    下面是使用char与varcahr的一些结果。

   (1)数据存储开销。

      a. 每个varchar列需要额外的两个字节,用于反映存储的数据的长度。

      b. 每个可为NULL的char列,需要一些字节(空位图)来反应数据的为空性。

      c. 无论实际数据的长度是多少,char按照定义的长度分配存储空间。

    (2) NULL值。

      a. char列的NULL值占用存储空间。

      b. varcahr列的NULL值不占用存储空间。

      c. 插入同样数量的NULL值,varchar列的插入效率明显高出char列。

    (3) 插入数据。

      无论插入数据涉及的列是否建立索引,char的效率都明显低于varchar。

    (4) 更新数据

      如果更新的列上未建立索引,则char的效率低于varchar,差异不大;建立索引的话,效率差异较大。

   (5) 修改结构

      a. 无论增加或是删除的列的类型是char还是varchar,操作都能较快的完成,而且效率上没有什么差异。

      b. 对于增加列的宽度而言,char与varchar有非常明显的效率差异,修改varcahr列基本上不花费时间,而修改char列需要花费很长的时间。

   (6) 数据检索。

      无论是否通过索引,varchar类型的数据检索略优于char的扫描。

选择char还是选择varchar的建议:

    (1) 适宜于char的情况:

      a. 列中的各行数据长度基本一致,长度变化不超过50字节;

      b. 数据变更频繁,数据检索的需求较少。

      c. 列的长度不会变化(修改char类型列的宽度的代价比较大)

      d. 列中不会出现大量的NULL值。

      e. 列上不需要建立过多的索引(过多的索引对char列的数据变更影响较大)

   (2) 适宜于archar的情况:

       a. 列中的各行数据的长度差异比较大。

      b. 列中数据的更新非常少,但查询非常频繁。

       c. 列中经常没有数据,为NULL值或为空值。

转载于:https://www.cnblogs.com/zhangchaoran/p/7326898.html

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
nvarcharvarcharSQL Server用于存储字符数据的数据类型。它们的用法基本相同,但在一些方面有所不同。 nvarchar是用于存储Unicode字符数据的可变长度数据类型。它可以存储最多4,000个字符,每个字符占用2个字节的存储空间。在比较字符数据时,nvarchar会考虑Unicode字符的排序规则和大小写区分等特性。在定义nvarchar列时,需要指定最大字符数,例如nvarchar(50)表示该列最多可以存储50个字符。在使用nvarchar存储Unicode字符串常量时,需要在字符串前加上N来指定,例如N'这是一个Unicode字符串'。 而varchar是用于存储非Unicode字符数据的可变长度数据类型。它也可以存储最多4,000个字符,每个字符占用1个字节的存储空间。在比较字符数据时,varchar只考虑字符的排序规则和大小写区分等特性,不考虑Unicode字符的规则。与nvarchar类似,在定义varchar列时,也需要指定最大字符数,例如varchar(50)表示该列最多可以存储50个字符。 总之,nvarcharvarchar都是用于存储字符数据的数据类型,但nvarchar用于存储Unicode字符数据,而varchar用于存储非Unicode字符数据。它们的存储大小和排序规则等方面有所不同。<span class="em">1</span><span class="em">2</span><span class="em">3</span> #### 引用[.reference_title] - *1* [使用 Unicode 数据 ](https://blog.csdn.net/zshwlw/article/details/1624709)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 33.333333333333336%"] - *2* [SQLvarchar和nvarchar的基本介绍及其区别](https://download.csdn.net/download/weixin_38606294/13696521)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 33.333333333333336%"] - *3* [oracle对char 和varchar 类型如何比较](https://blog.csdn.net/weixin_39946266/article/details/116315495)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 33.333333333333336%"] [ .reference_list ]
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值