使用 PHP 解譯 javascript escape() 編碼過的字串

使用 PHP 解譯 javascript escape() 編碼過的字串

PHP 跟 Javascript 都有 HTML encoding 的函式,編碼過的結果雖然類似,但是還是有些微的不同,所以不能互轉。

二者的差異可以可參考:
http://web.archive.org/web/20030811181238/http://php.weblogs.com/php_jscript_vbscript_1

節錄如下:

PHP:
urlencode( ) All punctuation, accented characters, and any other non-ASCII characters are replaced with %xx encoding. Spaces converted to +.

urldecode( )All punctuation, accented characters, and any other non-ASCII characters are replaced with %xx encoding. Spaces converted to +.

Javascript:
escape(str) All spaces, punctuation, accented characters, and any other non-ASCII characters are replaced with %xx encoding

那要如何用 PHP 來讀取 escape() 編碼過的字串呢?

可以用以下的方式來讀取 (範例為 Unicode 解譯為 big5)

修改自:http://web.archive.org/web/20041031225806/http://vivian.stripper.jp/index.php?itemid=100

$str = uniDecode($str,'big-5');

function uniDecode($str,$charcode){
$text = preg_replace_callback("/%u[0-9A-Za-z]{4}/",toUtf8,$str);
return mb_convert_encoding($text, $charcode, 'utf-8');
}
function toUtf8($ar){
foreach($ar as $val){
$val = intval(substr($val,2),16);
if($val < 0x7F){ // 0000-007F
$c .= chr($val);
}elseif($val < 0x800) { // 0080-0800
$c .= chr(0xC0 | ($val / 64));
$c .= chr(0x80 | ($val % 64));
}else{ // 0800-FFFF
$c .= chr(0xE0 | (($val / 64) / 64));
$c .= chr(0x80 | (($val / 64) % 64));
$c .= chr(0x80 | ($val % 64));
}
}
return $c;
}

附上delphi对escape的处理代码:

function Escape(const StrToEscape:WideString):String;
var
   i:Integer;

   w:Word;
begin
     Result:='';

     for i:=1 to Length(StrToEscape) do
     begin
          w:=Word(StrToEscape[i]);

          if w in [Ord('0')..Ord('9'),Ord('A')..Ord('Z'),Ord('a')..Ord('z')] then
             Result:=Result+Char(w)
          else if w<=255 then
               Result:=Result+'%'+IntToHex(w,2)
          else
               Result:=Result+'%u'+IntToHex(w,4);
     end;
end;

procedure TForm1.FormCreate(Sender: TObject);
begin
     Caption:=Escape('aA 中文0 Bb');
end;

function Unescape(const StrEscaped:String):WideString;
          function UnescapeUncodeChar(const s:String):WideChar;
          var
             r:Array [0..1] of Byte;
          begin
               HexToBin(
                        PChar(LowerCase(s)),
                        @r,
                        SizeOf(r)
                        );
               Result:=WideChar((r[0] shl 8) or r[1]);
          end;
          function UnescapeAnsiChar(const s:String):Char;
          begin
               HexToBin(
                        PChar(LowerCase(s)),
                        @Result,
                        SizeOf(Result)
                        );
          end;
var
   i:Integer;

   c:Integer;
begin
     c:=1;
     SetLength(Result,Length(StrEscaped));

     i:=1;
     while i<=Length(StrEscaped) do
     begin
          if StrEscaped[i]='%' then
          begin
               if (i<Length(StrEscaped)) and (StrEscaped[i+1]='u') then
               begin
                    Result[c]:=UnescapeUncodeChar(
                                                  Copy(
                                                       StrEscaped,i+2,4
                                                       )
                                                  );//Do with '%uxxxx'
                    Inc(i,6);
               end
               else
               begin
                    Result[c]:=WideChar(
                                        UnescapeAnsiChar(
                                                         Copy(StrEscaped,i+1,2)
                                                         )
                                        );//Do with '%xx'
                    Inc(i,3);
               end;
          end
          else
          begin
               Result[c]:=WideChar(StrEscaped[i]);

               Inc(i);
          end;

          Inc(c);
     end;

     SetLength(Result,c-1);
end;

procedure TForm1.FormCreate(Sender: TObject);
begin
     Caption:=Unescape('aA%65%u4E2D%u6587%64Bb');
end;

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值