2009-05-26 95 views
7

我有一个MySQL表,120,000行以UTF-8格式存储。有一个字段,产品名称,其中包含许多重音的文本。在将其转换为URL友好形式(ASCII)后,我需要使用相同的名称填充第二个字段。iconv用“聪明的引号”给出了“非法字符” - 如何摆脱它们?

由于PHP不直接处理UTF-8,我使用的是:

 
$value = iconv ('UTF-8', 'ISO-8859-1', $value); 

的名称为ISO-8859-1,其次是一个巨大的声明的strstr转换通过更换任何重音字符它的不相关的等价物(例如à变成a)。

然而,原始文本名称用智能引号进入和iconv扼流圈每当它遇到一个 - 我得到:

 
Unknown error type: [8] 

iconv() [function.iconv]: Detected an illegal character in input string 

要使用的iconv之前摆脱智能引号的,我曾尝试用三句话一样:

 
$value = str_replace('’', "'", $value); 

(A€™是UTF-8的智能单引号的原始值)

由于文本文件是这么久,这些str_replace函数的事业日e脚本每次都会超时。

  1. 什么是去掉从UTF-8字符串中的智能引号(或任何无效字符),运行的iconv之前,最快的方法是什么?

  2. 或者,有没有更容易解决这个问题?以UTF-8格式将带有许多重音的名称转换为不带重音的名称,以ASCII格式正确拼写的最快方法是什么?

+2

你试过iconv()的// TRANSLIT能力了吗?它应该将重音字符转换为可读的ASCII等价物。 – ceejayoz 2009-05-26 16:39:36

+0

我正在查看文档,但我不明白它将如何帮助 - 如果iconv()已经扼杀了智能报价,如果我使用// TRANSLIT,它会不会窒息? – 2009-05-26 16:45:30

+0

这更适用于你的“大规模的strstr声明” - 这就是为什么我发表评论而不是回答。 – ceejayoz 2009-05-26 16:59:08

回答

2

“链接友好”是什么意思?只有这样我才有意义,因为<a>...</a>标签之间的文本可以是任何东西,实际上是“URL友好”的,类似于SO的URL,其中所有东西都被转换为[a-z-]

如果这就是你要做的,你需要一个音译库,而不是一个字符集转换库。 (过去我没有让iconv()做这项工作,但我还没有尝试过。)有一个测试PHP扩展translitprobably does the job

如果你不能添加扩展到你的PHP安装,你将不得不寻找一个PHP库来做同样的事情。我没有使用它,但PHP UTF-8库实现了一个utf8_to_ascii库,我假设你做了类似你需要的东西。如果iconv()失败,就像你说的那样,这意味着你的输入实际上并不是有效的UTF-8,所以用其他任何东西代替有效的UTF-8都不会有助于解决这个问题。编辑:我可以回想一下:如果ephemient's answer是正确的,你看到的iconv错误很可能是因为目标字符集中没有字符的直接表示。所以,从来不知道。)

0

你有没有考虑过使用MySQL的REPLACE字符串函数将有问题的字符串更改为撇号或其他?您可以将“要替换的字符串”部分放在一起,例如在CHAR上使用CONCAT调用...

6

Glibc(和GNU libiconvsupports//TRANSLIT//IGNORE后缀。

因此,在Linux上,这工作得很好:

 
$ echo $'\xe2\x80\x99' 
’ 
$ echo $'\xe2\x80\x99' | iconv -futf8 -tiso8859-1 
iconv: illegal input sequence at position 0 
$ echo $'\xe2\x80\x99' | iconv -futf8 -tiso8859-1//translit 
' 

我不知道什么是iconv通过PHP的使用,但文档意味着//TRANSLIT//IGNORE将在那里工作过。