티스토리 뷰

대만에서쓰는 중국어 번체자를 처리하기 위해서 작업을 하는 중에

php의 strtoupper() 함수에서 오작동을 하는 것을 발견하였습니다.

그래서 구글링을 해서 아래와 같은 소스로 처리할 수 있었습니다.

mbstring api을 쓴다면 아마 필요 없을 것입니다. :-)


<?php
/*
  php에서의 big5 문자열 함수 모음

  파일: big5_func.php
  출처: Pigo Chu<pigo@ms5.url.com.tw>
  수정: J. Seo <dino412@gmail.com>
 

  string big5_addslashes(string str) : addslashes 함수와 같음.
  string big5_stripslashes(string str) : stripslashes 함수와 같음.
  int big5_strlen(string str) : 문자열의 길이를 반환
  string big5_substr(string str,int start , int length) : 문자열 일부를 반환
  string big5_strtolower(string str) : BIG5 문자를 제외한 소문자 전환
  string big5_strtoupper(string str) : BIG5 문자를 제외환 대문자 전환
 
*/

define("BIG5_FILE_DIR" , DIR_FS_CATALOG . DIR_WS_INCLUDES . "tchinese");

define("BIG5_HB_MIN" , 0x81);
define("BIG5_HB_MAX" , 0xfe);
define("BIG5_LB1_MIN" , 0x40);
define("BIG5_LB1_MAX" , 0x7e);
define("BIG5_LB2_MIN" , 0xa1);
define("BIG5_LB2_MAX" , 0xfe);

function big5_isHB($c) {
  $asc = Ord($c);
  if($asc>=BIG5_HB_MIN && $asc<=BIG5_HB_MAX) return true;
  return false;
}

function big5_isLB($c) {
  $asc = Ord($c);
  if(($asc>=BIG5_LB1_MIN && $asc<=BIG5_LB1_MAX)  || ($asc>=BIG5_LB2_MIN && $asc<=BIG5_LB2_MAX))
      return true;
  return false;
}

function big5_global_func($str,$func)
{
   $return_str = "";
   for($i=0; $i
   {
       $isHB = 0;              // BIG5 시작바이트
       $isLB = 0;              // BIG5 끝바이트
       $s1 = substr($str,$i,1);
       if(!$isHB && big5_isHB($s1)) // 시작바이트인지 검사
       {
           $isHB = 1;
           $s2 = substr($str,$i+1,1);
           if( big5_isLB($s2) )  // 끝바이트도 맞는지 검사
             $isLB = 1; 
       }
       if($isLB && $isHB) {
           $return_str.= $s1.$s2;
           $i++;
       }
       else
       {
           switch($func)
           {
               case "addslashes":
                   $return_str.= addslashes($s1);
                   break;
               case "stripslashes":
             
                   if($s1 == "\\")
                   {
                       $s2 = substr($str,$i+1,1);
                       if($s2  == "\\")
                           $return_str .= "\\";
                       else
                           $return_str .=$s2 ;
                       $i++;

                   }
                   else $return_str .=$s1;
                   break;
             
               case "strtolower":
                   $return_str.= strtolower($s1);
                   break;
               case "strtoupper":
                   $return_str.= strtoupper($s1);         
                   break;
           }
       }
   }
 

   return $return_str;
}

function big5_addslashes($str) {
   return big5_global_func($str,"addslashes");
}
function big5_stripslashes($str) {
   return big5_global_func($str,"stripslashes");
}
function big5_strtolower($str) {
   return big5_global_func($str,"strtolower");
}
function big5_strtoupper($str) {
   return big5_global_func($str,"strtoupper");
}
function big5_str_replace($search , $replace, $subject)
{
   for($i=0; $i
   {
       $isHB = 0;              // BIG5 시작바이트
       $isLB = 0;              // BIG5 끝바이트
       $s1 = substr($subject,$i,1);
       if(!$isHB && big5_isHB($s1))
       {
           $isHB = 1;
           $s2 = substr($subject,$i+1,1);
           if( big5_isLB($s2) )
             $isLB = 1; 
       }
       if($isLB && $isHB)
       {
           $first_str = $s1.$s2;
           if($first_str == substr($search,0,2))
           {
               if( substr($subject,$i,strlen($search)) == $search )
               {

                   $return_str .= $replace;
                   $i+=strlen($search)-1;
               }
               else
               {
                   $return_str .= $first_str;
                   $i++;
               }
           }
           else
           {
               $return_str .= $first_str;
               $i++;
           }
       }
       else
       {
           $first_str = $s1;
           if($first_str == substr($search,0,1))
           {
               if( substr($subject,$i,strlen($search)) == $search )
               {

                   $return_str .=  $replace;
                   $i+=strlen($search)-1;
               }
               else $return_str .= $first_str;
           }
           else $return_str .= $first_str;
       }
   }
   return $return_str;
}


function big5_strlen($str)
{
   $return_len = 0;
   for($i=0; $i
   {
       $isHB = 0;
       $isLB = 0;
       $s1 = $str[$i];
       if(!$isHB && big5_isHB($s1))
       {
           $isHB = 1;
           $s2 = $str[($i+1)];
           if( big5_isLB($s2) )
             $isLB = 1; 
       }
       if($isLB && $isHB) $i++;
       $return_len++;
   }
   return $return_len;
}

function big5_substr($str,$start,$len=0)
{
   $offset = 0;
   if(!$len) $len = strlen($str);
   $str_len =  strlen($str);
   $start = $start-1;
   for($i=0; $i< $str_len; $i++)
   {
     if($offset>$start)
     {
       if(big5_isHB($str[$i]) && big5_isLB($str[($i+1)]))
       {
               $return_str .= $str[$i].$str[$i+1];
               $i++;
       }
       else $return_str .= $str[$i];
       if($offset-$start >= $len) break;
     }
     else if(big5_isHB($str[$i]) && big5_isLB($str[($i+1)]))
         $i++;
     $offset ++;
   }
   return $return_str;
}

 

function big5_strpos($haystack ,$needle ,$offset=0)
{
    $needle_len = big5_strlen($needle);
    $len =big5_strlen($haystack);
    for($i=$offset ; $i<$len ; $i++)
    {
        if(big5_substr($haystack,$offset+$i,$needle_len) == $needle)
            return $i;
    }
    return false;
}

function big5_chunk_split($str, $chunklen=76 , $end="\r\n")
{
   for($i=0 ; $i      return big5_substr($str,$i,$chunklen) .$end;
}


function big5_stroke($str)
{
    $tab=@File(BIG5_FILE_DIR  ."/big5_stroke.tab");
    if(!$tab)
    {
            echo "Can't Open file big5_stroke.tab, plz check define BIG5_FILE_DIR is valid";
            exit;
    }
    /* $StrokeMapping */
    $i=0;
    while(list($key,$val)=Each($tab))
    {
        $StrokeMapping[$i] = split(" ",$val);
        $StrokeMapping[$i][1] = HexDec($StrokeMapping[$i][1]);
        $StrokeMapping[$i][2] = HexDec($StrokeMapping[$i][2]);
        $i++;
    }

    $s1 = substr($str,0,1);
    $s2 = substr($str,1,1);
    $s  = Hexdec(Bin2hex($s1.$s2));
  
    if( big5_isHB($s1) && big5_isLB($s2) )
    {
        for($i=0;$i
             if($StrokeMapping[$i][1] <= $s && $StrokeMapping[$i][2] >= $s)
                 return $StrokeMapping[$i][0];
    }
    else
        return false;
}

function big5_unicode($str)
{
    $tab=@File(BIG5_FILE_DIR  ."/big5_uni.tab");
  
    if(!$tab)
    {
            echo "Can't Open file big5_uni.tab, plz check define BIG5_FILE_DIR is valid";
            exit;
    }
    /* $UNICODE */
    while(list($key,$val)=Each($tab))
        $UNICODE[substr($val,0,4)] = substr($val,5,4);
    // unset($tab);
    $str_len =  strlen($str);

    for($i=0; $i< $str_len; $i++)
    {
      if(big5_isHB($str[$i]) && big5_isLB($str[($i+1)]))
      {
          $s = $str[$i].$str[$i+1];
          $i++;
      }
      else $s = $str[$i];

        if(strlen($s) == 1)
           $ret_str .= "&#" . Hexdec(bin2hex($s)) . ";";
        else
           $ret_str .= "&#" . hexdec($UNICODE[bin2hex($s)]) . ";";
    }

    return $ret_str;
}

 

function big5_utf8_encode($str)
{
    // big5 to utf8
    $tab = unserialize(@fread(@fopen(BIG5_FILE_DIR  ."/big5_utf8.tab" , "r"),fileSize(BIG5_FILE_DIR  ."/big5_utf8.tab")));

    if(!is_array($tab))
    {
            echo "Can't Open file big5_utf8.tab, plz check define BIG5_FILE_DIR is valid";
            exit;
    }
   $str_len =  strlen($str);
   for($i=0; $i< $str_len; $i++)
   {
      if(big5_isHB($str[$i]) && big5_isLB($str[($i+1)]))
      {
          $s = $str[$i].$str[$i+1];
          $i++;
      }
      else $s = $str[$i];
      $ret_str.= $tab[bin2hex($s)];
   }
   return $ret_str;
}

function big5_utf8_decode($str)
{
    // utf8 to big5
    $tab = unserialize(@fread(@fopen(BIG5_FILE_DIR  ."/utf8_big5.tab" , "r"),fileSize(BIG5_FILE_DIR  ."/utf8_big5.tab")));

    if(!$tab)
    {
            echo "Can't Open file utf8_big5.tab, plz check define BIG5_FILE_DIR is valid";
            exit;
    }

    $len = strlen($str);
    for($i=0 ; $i<$len ; $i++)
    {
           $check = Ord($str[$i]);
        if( $check >> 7 == 0)
            $ret_str .= chr($check);

        else if ( $check>>5 == 6 ) // AscII > 127
        {
            $ret_str .= $tab[bin2hex($str[$i].$str[$i+1])];
            $i++;
        }
        else if ( $check>> 4 == 0xe)
        {
             $ret_str .= $tab[bin2hex($str[$i].$str[$i+1].$str[$i+2])];
            $i+=2;
        }

    }
   return $ret_str;
}

?>


댓글
댓글쓰기 폼