2012-01-18 16 views
0

BOMエンコーディングを使用しないでUTF-8のCSVファイルをチェックする方法はありますか?私はファイル全体をチェックしたいが、単一の文字列ではない。csvファイルがPHPでUTF-8であることを確認

最初の行に特殊文字を設定し、その文字列を読み込み、スクリプト内でハードコードされた同じ文字列と一致するかどうかを確認するようにします。しかし、これが良い考えであるかどうかはわかりません。

Googleのみshowed me this。しかし、最後の投稿のリンクは利用できません。

答えて

8
if (mb_check_encoding(file_get_contents($file), 'UTF-8')) { 
    // yup, all UTF-8 
} 

ファイルが大きく、一度にメモリにすべてを保存したくない場合にも、fgetsとのラインでそれラインを通って行くことができます。あなたの質問の第二の部分が何を意味するかわからない。

+0

この関数は、不正なバイトシーケンスをチェックしません。バイトストリームが有効かどうかを確認します。 – Damien

+0

@Damien正確に何を意味するのかを明確にすることができれば感謝します。それは不正な形式のUTF-8バイトシーケンスをキャッチします。そのため、「不良バイトシーケンス」は何ですか? http://codepad.viper-7.com/6yvKe9。 – deceze

+0

UTF-8でサロゲートをキャッチしないこの機能に関する[バグレポート](https://bugs.php.net/bug.php?id=47990)がありますが、私は[それを再現できません](http: /codepad.viper-7.com/DFz1nJ)を参照してください。 – deceze

4

私は(symfonyのツールキットから)この機能をrecommand:

<?php 
    /** 
    * Checks if a string is an utf8. 
    * 
    * Yi Stone Li<[email protected]> 
    * Copyright (c) 2007 Yahoo! Inc. All rights reserved. 
    * Licensed under the BSD open source license 
    * 
    * @param string 
    * 
    * @return bool true if $string is valid UTF-8 and false otherwise. 
    */ 
    public static function isUTF8($string) 
    { 
    for ($idx = 0, $strlen = strlen($string); $idx < $strlen; $idx++) 
    { 
     $byte = ord($string[$idx]); 

     if ($byte & 0x80) 
     { 
     if (($byte & 0xE0) == 0xC0) 
     { 
      // 2 byte char 
      $bytes_remaining = 1; 
     } 
     else if (($byte & 0xF0) == 0xE0) 
     { 
      // 3 byte char 
      $bytes_remaining = 2; 
     } 
     else if (($byte & 0xF8) == 0xF0) 
     { 
      // 4 byte char 
      $bytes_remaining = 3; 
     } 
     else 
     { 
      return false; 
     } 

     if ($idx + $bytes_remaining >= $strlen) 
     { 
      return false; 
     } 

     while ($bytes_remaining--) 
     { 
      if ((ord($string[++$idx]) & 0xC0) != 0x80) 
      { 
      return false; 
      } 
     } 
     } 
    } 

    return true; 
    } 

しかし、それは文字列のすべての文字をチェックして、私は大きなファイルにそれを使用するrecommandはありません。つまり、最初の10行をチェックするだけです。

<?php 
$handle = fopen("mycsv.csv", "r"); 
$check_string = ""; 
$line = 1; 
if ($handle) { 
    while ((($buffer = fgets($handle, 4096)) !== false) && $line < 11) { 
     $check_string .= $buffer; 
     $line++; 
    } 
    if (!feof($handle)) { 
     echo "Error: unexpected fgets() fail\n"; 
    } 
    fclose($handle); 

    var_dump(self::isUTF8($check_string)); 
} 
関連する問題