2012-06-13 65 views
7

我正在爲國際客戶工作,他們擁有所有非常不同的字母,因此我試圖最終獲得PHP和MySQL之間的完整工作流程概述,以確保所有字符編碼能夠正確插入。我已經閱讀了一些關於這方面的教程,但仍然有問題(有很多需要學習的內容),並且認爲我可能會將它們放在一起並詢問。UTF8工作流程PHP,MySQL彙總

PHP

header('Content-Type:text/html; charset=UTF-8'); 
mb_internal_encoding('UTF-8'); 

HTML

<meta http-equiv="Content-Type" content="text/html;charset=UTF-8"> 
<form accept-charset="UTF-8"> .. </form> 

(雖然後來是可選的,而是一個建議,但我相信我寧願建議不會做任何事情)

MySQL

CREATE database_name DEFAULT CHARACTER SET utf8;ALTER database_name DEFAULT CHARACTER SET utf8;和/或使用utf8_general_ci作爲MySQL連接歸類。

(這是important to note這裏,這將增加數據庫的大小,如果它使用VARCHAR)

連接

mysql_query("SET NAMES 'utf8'"); 
mysql_query("SET CHARACTER_SET utf8"); 

業務邏輯

檢測如果不是UTF8與mb_detect_encoding()並用ivon()轉換。
驗證UTF8和UTF16的超長序列

$body=preg_replace('/[\x00-\x08\x10\x0B\x0C\x0E-\x19\x7F]|(?<=^|[\x00-\x7F])[\x80-\xBF]+|([\xC0\xC1]|[\xF0-\xFF])[\x80-\xBF]*|[\xC2-\xDF]((?![\x80-\xBF])|[\x80-\xBF]{2,})|[\xE0-\xEF](([\x80-\xBF](?![\x80-\xBF]))|(?![\x80-\xBF]{2})|[\x80-\xBF]{3,})/','�',$body); 
$body=preg_replace('/\xE0[\x80-\x9F][\x80-\xBF]|\xED[\xA0-\xBF][\x80-\xBF]/S','?', $body); 

問題

  • 是必要的,PHP 5.3和更高mb_internal_encoding('UTF-8')如果是的話這是否意味着我必須使用所有的多字節函數來代替其核心功能如mb_substr()而不是substr()

  • 是否仍然需要檢查格式錯誤的輸入刺激,如果是的話,那麼可靠的函數/類是如何執行的?我可能不想去掉不好的數據,也不太瞭解音譯。

  • 它應該是utf8_general_ci還是utf8_bin

  • 在上述工作流程中是否有缺失?

來源:

http://coding.smashingmagazine.com/2012/06/06/all-about-unicode-utf8-character-sets/ 
http://webcollab.sourceforge.net/unicode.html 
http://stackoverflow.com/a/3742879/1043231 
http://www.adayinthelifeof.nl/2010/12/04/about-using-utf-8-fields-in-mysql/ 
http://akrabat.com/php/utf8-php-and-mysql/ 
+1

好了,問題是什麼? –

+0

對不起,我用,因爲它似乎計算器錯誤我的一些源鏈接的代碼和拋出一個錯誤張貼這個問題掙扎....現在的工作... – Dominik

+0

mb_internal_encoding需要(「UTF-8」),如果mb_internal_encoding()結果不是UTF-8。 – 2012-06-13 12:05:04

回答

1

如果真的是utf8_general_ci或者說utf8_bin?

必須使用utf8_bin爲區分大小寫搜索,否則utf8_general_ci

是mb_internal_encoding( 'UTF-8')有必要在PHP 5.3及以上,如果是這是否意味着我必須使用所有多字節函數而不是像mb_substr()而不是substr()這樣的核心函數?

當然是的,如果你有一個多字節字符串你需要MB_ *家庭功能一起工作,除了像str_replace函數二進制安全PHP的標準功能(); (和其他幾個人)

是否仍然需要檢查格式錯誤的輸入刺激,如果是的話,那麼可靠的函數/類是什麼?我可能不想去掉不好的數據,也不太瞭解音譯。

嗯,沒有你不能檢查。

+3

第二和第三點是不現實的。第二點取決於「過濾」的內容......例如,您仍然可以執行'(int)$ _ GET ['utf8var']'。PHP的字符串函數是二進制的。除非你搞砸了,'str_replace()'和家族仍然有效(唯一的例外是UTF8別名)。 – Christian

6
  • mb_internal_encoding('UTF-8')本身不做任何事情,它只設置每個mb_函數的默認編碼參數。如果您沒有使用任何mb_功能,它沒有任何區別。如果是,則設置它是有意義的,因此您不必每次都單獨通過$encoding參數。
  • IMO mb_detect_encoding是大多無用,因爲它根本不可能準確地檢測未知文本的編碼。您應該知道什麼編碼的文本的BLOB是因爲你有一個規範它,或者你需要分析類似的報頭或在指定的編碼的meta標籤適當的元數據。
  • 使用mb_check_encoding檢查文本的斑點是否是你希望它是在編碼有效期通常是足夠的。如果不是,則丟棄它並拋出適當的錯誤。
  • 關於:

    這是否意味着我必須使用的,而不是它的核心功能

    如果你操縱包含多字節字符的字符串的所有多字節的功能,那麼,你需要使用mb_函數來避免出現錯誤的結果。核心字符串函數只能在字節級別上工作,而不能在字符級別上工作,這是您使用字符串時通常需要的。

  • utf8_general_ciutf8_bin只有當整理,即排序和比較字符串時纔會有所不同。用utf8_bin數據以二進制形式處理,即只有相同的數據是相同的。使用utf8_general_ci應用了一些邏輯,例如, 「é」與「e」一起排列,大寫字母等同於小寫字母。