在php中为utf_unicode_ci准备唯一值

时间:2013-03-22 18:07:57

标签: php character-encoding collation unique-constraint

我需要从PHP中读取ISO-8859-1编码文件中的值,并使用PDO将它们写入编码为utf8_unicode_ci且具有唯一索引的数据库表。有时,数据缺少特殊字符,导致重复键错误。示例:数据包含“Entrainement”和“Entraînement”。我可以使用PHP字符串函数来避免这种情况吗?

最好是转换函数,所以我不必迭代整个数组来检查是否已经插入了一个值。

以下是我正在尝试做的一个例子:

$values = array("Entraînement", "Entrainement");
$db = new PDO("mysql:dbname=mydb;host=localhost;charset=utf8", "user", "pw");
$db->exec("SET NAMES 'UTF-8'");
$stmt = $db->prepare("INSERT INTO mytable(myvalue) VALUES(?)");
$already_inserted = array();
foreach($values as $v) {
    $v = $v_inserted = iconv('iso-8859-1', 'utf-8', $v);
    // Do magic string conversion here
    // $v_inserted = collation_convert($v_inserted)
    if(isset($already_inserted[$v_inserted])) {
        continue;
    }
    if($stmt->execute(array($v))) {
        $already_inserted[$v_inserted] = true;
    }

}

此示例应仅插入“Entraînement”并跳过“Entrainement”。

在原始程序中,我使用的是Doctrine ORM而不是PDO,因此我可以在SQL中做很多事情。另外,我在整个Latin1范围内都有特殊的字符 - 法语,德语,西班牙语等。

我无法将数据库字段定义更改为utf8_bin,因为它是电子商务包的一部分 - 各种各样的事情可能会中断。

1 个答案:

答案 0 :(得分:1)

那么你肯定应该将值转换为UTF-8并使用UTF-8连接编码。否则,您的应用程序根本无法利用UTF-8,因为您的应用程序只能发送和接收ISO-8859-1包含的字符。与Unicode☹相比,这是非常非常少的。


这与您的问题*无关,在unicode_ci归类中,î被视为与i相同。 如果您需要将它们视为不同的字符,请使用其他一些排序规则:

SELECT 'î' = 'i' COLLATE 'utf8_unicode_ci'
//1

SELECT 'î' = 'i' COLLATE 'utf8_bin'
//0

没有德国**校对,所以我想utf8_bin就是你想要的。


*当声明的连接编码与您发送的物理字节的编码不匹配时,只会出现问题。 I.E.如果您使用UTF-8连接编码发送ISO-8859-1字节,如果没有错误,您将得到废话。反之亦然。

**我从你的个人资料中看到了这个,如果你实际上需要一些其他语言可能会有一个整理。