网站导航免费论文 原创论文 论文搜索 原创论文 网学软件 学术大家 资料中心 会员中心 问题解答 原创论文 论文素材 设计下载 最新论文 下载排行 论文上传 在线投稿 联系我们
返回网学首页
最新论文 推荐专题 热门论文 素材专题
当前位置: 网学 > 网页素材 > AJAX代码 > 正文
ExtJS 2.2string操作
来源:Http://myeducs.cn 联系QQ:点击这里给我发消息 作者: 用户投稿 来源: 网络 发布时间: 11/01/18
返回深入学习ExtJS 2.2开发系列连载教程目录
3.4 String操作
String是JavaScript中原始类型,其string文本形式可以通过一些方式构建成其它类型,如new Function可以通过指定string文本来动态构建函数内容。eval函数可以通过指定的string文本可以动态构建JavaScript对象和正在执行的语句。而每个基本类型都有着对应的string文本。可以看出JavaScript的一切对象及实现都源自string文本。

我们可以把字符处理分成三种:字符编码处理,格式化处理,进行转换处理。

3.4.1字符编码
字符(char)是一个抽象意义上的符号。而计算机中都是二进制的数字编码的地址。在计算机中是通过该地址来代表某一个字符。在绝大多数语言中(如Java)都有Byte类型,根据指定的数字编码来定位一个字符空间。

该地址代表什么字符,对于一个特定字符(如a)用什么数值的地址形式表示呢?这就是采用一种标准来规定,最早的编码标准是ASCII码规范。它通过一个字节的长度(256)来表示英文中使用到的字母、数字及一些特殊符号。如0X30~0X39代表0~9的数字字符,0X61-0X7A代表a-z的小写字母。但是其只用到前面126个单元。

采用Byte数值形式表示字符在编码实现中一点都不直观,每门语言都会提供Char类型用字符符号来直接定义表示。如’a’就是表示其字符,不必记忆0x61这样的数值编码。但是有些字符是非显示字符,没有对应的符号,如回车。那么通过Char类型就得进行转义了。

在JavaScript中有如下几种转义字符:"\b", "\t", "\n","\f"'', "\r",''"'',"\\" 。它们看上是两个字符。但是在解析时会解析成一个字符的ASCII码。然有时对于它们,并不想转义怎么办?如\n就是要表示两个字符,那得采用\把\给转义掉,其处理为\\n。JavaScript字符串编码解析时就是在遇到\就会把其后单个字符组合起来,看看其是否为转义字符,是找到其对应的ASCII字符数值编码,如否,则把\给删除。如alert("\t\a\c"),其结果是ac,其字符长度为3,因\t转义字符不可见但有长度。

ASCII只能满足英文编码的需要,非英文国家如果要进行其国家语言计算化就得采用其它的编码方式。如汉字至少有6千个汉字,而8位的字节长度怎么去表示呢。这时就出现了ANSI编码标准。每个国家都可以在该基础上进行各自的语言编码。

ANSI编码标准兼容于ASCII码,采用二位字节去表示一个符号,这样就会有65,536(2的16次方) 个字符。但是为了兼容于ASCII码,其字节首位是用来区分的标识,如其为1,就表示是采用二位字节长度的编码,如果是0就表示是采用ASCII码。这样其实只能表示128*128个扩展字符。基本上能满足每个国家语言的需要。

当解析时碰到其字节首为1,该编码方式就会组合连续两个字节来找到该字符。所以对于汉字和字母组合的字符串,它的长度是不一样的,如“中国a”其长度为5个字节,但JavaScript采用宽字符表示,其长度为3。不同国家有不同ANSI编码,中国就有gb2312,GBK等编码方式,台湾则采用BIG5。不同ANSI 编码的字符互不兼容,无法将两种不同ANSI编码的字符存储在同一段文本中。

为了使国际信息交流更加方便,国际组织制定Unicode 字符集,为各种语言的字符设定统一且唯一的数字编号,以满足跨语言文本处理的要求。目前使用的 Unicode 版本采用16位编码空间,即每个字符占2个字节,包含ASCII码。每个符号都是唯一的数字编码,就不会出现各个语言之间的兼容问题

一个字符的 Unicode 编码是确定的。但是在实际传输过程中,其实现方式有所不同。其实现方式称为Unicode转换格式(Unicode Translation Format,简称为 UTF)。目前使用的转换格式为UTF-8。它是一种变长编码方式。能减少对于ASCII字符采用二个字符表示时造成的浪费。

JavaScript内部是采用Unicode的编码,所以我们可以直接在字符中采用\u00xx形式来表式某个Unicode字符。如alert("\u5B57\u6BB5名不能使用\x23");它显示的内容:字段名不能使用#。JavaSript提供一些函数如charAt和charCodeAt来进行编码方面处理。
string 编码测试 :var s = "中国aa\t\u5B57";
alert(s.charAt(0));// 中
alert(s.charCodeAt(0));// 20013
alert(s.charAt(4));// 没有显示出来
alert(s.charCodeAt(4));// 9
alert(s.charAt(5));// 字
alert(s.charCodeAt(5));// 23383    
从该例子可以看出charCodeAt把十六进制转换成十进制数字。charAt则能显示Unicode字符。String还提供静态方法fromCharCode完成十进制数字转换成字符。如String.fromCharCode(72,69,76,76,79))其结果是hello。

Html文件中显示字符和常规字符有点不一样。它对于一些特殊字符也是采用转义方式,如&à& 、>à>、"à"等。它们分别采用了一些其它的符号来进行代替,因为如果在html文件中,这些字符采用原始字符表示,就会和html标签中的字符相冲突。

这样一些特殊字符在显示时就得进行转换。Ext.util.Format类提供一对方法:htmlEncode和htmlDecode,从其名字也可以看出一个是把常规字符串转换成Html显示字符串,另外一个是把Html中文本转换成常规字符串。

3.4.2 字符串格式化
格式化处理是字符类型使用频率较高的功能部分。它能把某一字符串按指定的格式显示。在ExtJS对String提供了一些扩展方法。

leftPad函数。它的作用是如果指定字符串不满足要求的字符串长度,其指定字符串前面采用某些字符进行填充,使其达到一定长度。这个在金额报表中经常用到,如String.leftPad(''123'', 5, '' ''),这样就能让其金额的显示右对齐。 

format函数。它的作用是通过模板来进行格式化字符串。如var s = String.format(''<div class="{0}">{1}</div>'', cls, text);。其得到结果是''<div class="my-class">Some text</div>''。该函数可以实现强大的格式化功能。

对于字符串的格式化而言,除了上面的两个函数之后,ExtJS还专门提供了Ext.util.format类来进行字符串及日期等进行显示时的格式化转换。

省略。字符串超过一定长度的部分省略掉,省略部分…代替。这样能保证页面上排版不会出现溢出或其它问题。在实用中,主要是针对于显示的标题或摘写超长时进行省略,同时还会采用元素的title属性用来提示全部内容。ellipsis用来实现。 

默认值。字符串如果是空值,那么就采用默认的字符串进行显示替代。Ext.util.format中的defaultValue函数中,开发者可以参数来指定缺省值,而undef则是采用默认是空字符。

大小写。将字符串某些字符进行大小写变换。如lowercase把大写转为小写,uppercase则相反。capitalize是把字符串单词首字母大写。

除了这三部分,它还有一些其它的函数进行格式化,这里就不介绍。

3.4.3字符串与对象之间转换
通过 new String(obj)形式可以一个对象或原始类型数据转换成string类型数据。对于对象,它调用对象的tostring方法来进行转换。而对于Boolean、Float等原始类型,其采用内制的类型转换,Date.Format() :alert(new String(false));//false
alert(new String(3.25));//3.25
alert(new String({xx:"yy"}));//[object Object]
alert(new String(Object));//function Object(){[native Code]}
alert(new String([3,5,6]));//3,4,5
 该实例给出String构建函数如何转换Boolean,Number,Object,Fucntion,Array等类型的数据,可以看出object,function,array都是调用了其toString()方法。而Boolean,Number,类型,它们本身就有相对的string字符串(见《javascript权威教程第五版》)。在上例中对象的转换是不能满足要求。我们希望的结果是不是[object Object],而是{xx:"yy"}。对于数组,我们也是希望得到直观的其直接量字符串形式,如[3,5,6]。

上例是把对象转化成字符串,那么如果需要把字符串转化成对象呢?这时可以通过通过eval函数来实现。它就会字符串转化成其上下文中的对象,如eval("[x,y,z]")。

String和Json转换
我们可以在前面实例中看出对Object进行内查(Inspector)是件麻烦的事情。幸好ExtJS提供了Ext.encode函数把JSon对象转化其对应的字符串形式,Ext.decode则是把字符串形式转换成相对应JSon对象。下面我们通过实例子来看一下它能不能实现我们的要求:Ext.onReady(function(){
       var s={x1:''string'',x2:3.123,x3: new Date(),
x4:[[''aa'',false],2.3,{y1:''s'',y2:false}],x5:undefined,x6:true};      var o=Ext.encode(s);
   document.write(o);
}
);
上例中,我们首先给出一个JSon对象,之后通过Ext.encode来把它转换成文本形式,如果不采用Ext.encode进行转换,其结果字符串是[object Object],而现在其结果是:

{"x1":"string","x2":3.123,"x3":"2008-11-17T15:56:09","x4":

[["aa",false],2.3,{"y1":"s","y2":false}],"x6":true}

我们分析JSon对象,它定义x1到x6属性,x1值是字符串,返回也是字符串,x2值是数字,返回也是数字,x3值是Date对象,它会被执行并返回当前时间,x5值是undefined类型,其没有返回值。x6值是Boolean类型的true。它返回的是true。x4值是数组,该数组中又包含着数组,数字,对象三种类型,它返回的和其直接量内容相同的文本形式。

这种转换基本上符合我们的要求,其如何实现的呢?在解析其实现之前,我们回忆一下JavaScript六种类型:undefined、funciton、object、string、number、boolean。这其中Boolean,Number,String,Undefined、Funciton都可以通过new String()而得到相对的文本形式,而object类型则不一样,其可以细分成Date,Array等。

对于Array数组,可以通过它的toString()方法得到其内部所有元素内容。但这样有个问题,其内部元素如果是对象,还是不能进行转换,如[3,4,{xxx}]结果是3,4,[object Object]。对于Undefined类型,其返回的是Undefined文本形式,而在一般情况下,对象没有定义或设定值时,都会在转换化时过滤掉。对于Date对象,不应该采用默认是格林威治时间格式。

对于无序集合的JSON对象,其内部可以包含任何类型属性。对于它的处理,只要在其属性成功进行转换基础上,再加上{}把其属性内容给括起来就能得到对象的文本形式。而对于有序集合的Array数组。对处理Json对象是一样的,其不同在于其采用,而Json采用{}。

还有一些细节是要进行处理的,null对象应该怎么转换,转换成null字符串还是空字符呢?函数类型如果调用其toString()就可以显示其源码内容。Number类型则有NaN值的问题。对于这些,我们可以把对Json对象转换分解成几部分来单独处理,,如encodeString、encodeNull、encodeArray、encodeDate、encodeObject、encodeFunction、encodeBoolean、encodeNumber,之后采用encode把它们统一起来。对于Array和object的集合形式,当然要用上嵌套实现。我们看看Ext.util.json是如何实现:this.encode = function(o){
   if(typeof o == "undefined" || o === null){ return "null";}
   else if(Ext.isArray(o)){  return encodeArray(o);  }      ②
   else if(Ext.isDate(o)){    return encodeDate(o); }       ③
   else if(typeof o == "string"){  return encodeString(o); }
else if(typeof o=="number"){return isFinite(o)?String(o):"null";}
   else if(typeof o == "boolean"){    return String(o); }           ⑥
   else { var a = ["{"], b, i, v; ⑦
     for (i in o) {
      if(!useHasOwn || o.hasOwnProperty(i)) {  v = o[i];          ⑧    
         switch (typeof v) {                          ⑨
           case "undefined":
           case "function":
           case "unknown":   break;
           default:  if(b){ a.push('','');}                           ⑩
             a.push(this.encode(i),":",v===null?"null":this.encode(v));  
              b = true;  }} }

     a.push("});
    return a.join(""); }
"


}
;encode是入口函数,在其内部实现encodeNull, encodeObject、encodeBoolean、encodeNumber、encodeFunction等处理,其中①处是encodeNul实现,它把undefined和null都转换成null字符串。⑤处是encodeNumber实现,它把NaN值转换成null字符串。⑥处是encodeBoolean的实现,没有特殊处理。⑦处是encodeObject和encodeFunction的实现,对于函数,是取其静态属性,而非显示其源码。⑧处encodeObject实现中其把内部属性值为undefined或函数都解释成空对象{}。其它这里可以不必分离起来,而直接采用default中的处理。在⑩处,它是对对象的key和value都进行了转换。而encodeArray和ecnoceObject的实现差不多。接下来看看ecodeDate如何实现的。
var encodeDate = function(o){
    return ''"'' + o.getFullYear() + "-" +  pad(o.getMonth() + 1) + "-" +
            pad(o.getDate()) + "T" +pad(o.getHours()) + ":" +
            pad(o.getMinutes()) + ":" +pad(o.getSeconds()) + ''"''; };这一部分更为简单,它把格林威治时间采用如008-08-07T12:23:23的形式来显示。var encodeString = function(s){
    if (/["\\\x00-\x1f]/.test(s)) {//替换ansi码为0~31的特殊字符
        return ''"'' + s.replace(/([\x00-\x1f\\"])/g, function(a, b) {
           var c = m[b];
           if(c){ return c; }
           c = b.charCodeAt();  //把ansi转换为unicode
           return "\\u00"+Math.floor(c/16).
toString(16)+(c% 16).toString(16); }) + ''"'';}

  return ''"'' + s + ''"''; }
;
这里是进行转义还原的处理。也就是认为如\n的字符不是代表转义而代表两个字符。对于\x00-\x1f的其它字符则进行unicode转换。

查询字符串与对象转换
这是字符与对象之间的转换,但是在实际应用有一种使用频率特高的字符串与对象的之间转换,这个字符串是带有一定格式,即查询字符串。它通过attr=value对的字符形式来发现对象的属性与之对应的值。在form的提交等处理特常见。

下面我们就分别来看一下它们两者之间的处理。

上面讲到是Json直接量形式的字符串和对象之间的转换。其实在我们开发使用过程中,还有一种形式的字符串转换也是经常用到的,那就是查询字符串和Json对象之间的转换。比如在form提交传递后台数据时,都会把form中输入元素的值串成查询字符串的形式,有的时候我们也会用把查询字符串反编成对象的形式,这个便于在程序中使用。

在Ext中提供了统一的通用的实现。而在ajax中,它还提供了form所有的有效的元素转换成query string. 在Ext中这里提供了urlDecode和urlEncode来实现相互的转换。这里就通过urlEncode的源码来分析其实现:urlEncode : function(o){
   if(!o){ return ""; }
   var buf = ;
   for(var key in o){            
     var ov = o[key], k = encodeURIComponent(key);
     var type = typeof ov;
     if(type == ''undefined''){ buf.push(k, "=&");  }
else if(type != "function" && type != "object"){
        buf.push(k, "=", encodeURIComponent(ov), "&");  }

else if(Ext.isArray(ov)){  
       if (ov.length) {
           for(var i = 0, len = ov.length; i < len; i++) {
buf.push(k,"=",
encodeURIComponent(ov[i]===undefined?'''':ov[i]),"&");}}

else { buf.push(k, "=&");  }
         }

      }

     buf.pop();//最后一个元素
     return buf.join("");
  }
,
在上面的代码中,出现了encodeURIComponent,它是window方法。用来把字符串进行url形式的编码。该方法不会对 ASCII 字母和数字进行编码,也不会对这些 ASCII 标点符号进行编码: - _ . ! ~ * '' ( ) 。其他字符(比如 :;/?:@&=+$,# 这些用于分隔 URI 组件的标点符号),都是由一个或多个十六进制的转义序列替换的。

这个方法是通过对象的反射来找到该对象的每个属性。如果是undefined类型,它就采用空值,这个和空字符不一样,如xx=&,这里的&是查询字符串的分隔符号。如果是基本类型,就直接采用它的对应的字符形式,如xx=’aa’&。对于数组,它采用的转换是把数组的元素都采用相同的属性名,如xx=’e1’&xx=’e2’。在后台解析时,会把它们分析成数组的形式。

这里的转换只有一层,并没有多层的嵌套。下面我们通过一个例子不来演示一下其使用:var o={x1:''中国:?+=cfff'',x2:undefined,x3:,
x4:[2,3,''aa''],x4:true,x5:new Date(),x6:{y1:''aa''}};
document.write(Ext.urlEncode(o))
其结果是x1=%D6%90%3F%3F%2B%3Dcfff&x2=&x3=&x4=true。可以看出encodeURIComponent对于中文等都采用了转义序列的编码。它还只能解析一层,对于它内部的对象,它会省略。这里演示的是从对象到查询字符串的转换。urlDecode和它差不多,在这里就不重复介绍。
  • 上一篇资讯: ExtJS 2.2数据及集合
  • 下一篇资讯: ExtJS 2.2date的扩展
  • 网学推荐

    免费论文

    原创论文

    浏览:
    设为首页 | 加入收藏 | 论文首页 | 论文专题 | 设计下载 | 网学软件 | 论文模板 | 论文资源 | 程序设计 | 关于网学 | 站内搜索 | 网学留言 | 友情链接 | 资料中心
    版权所有 电话:013574892963 QQ:3710167 邮箱:Educs@163.com 网学网 [Myeducs.cn] 您电脑的分辨率是 像素
    Copyright 2008-2015 Www.myeducs.Cn All Rights Reserved
    湘ICP备09003080号