我有一个名字“Göran”,我希望将其转换为“ Goran ”,这意味着我需要 unaccent 特定的词。但我所尝试的似乎并非 unaccent 所有单词。
这是我用于Unaccent的代码:
private function Unaccent($string)
{
return preg_replace('~&([a-z]{1,2})(?:acute|cedil|circ|grave|lig|orn|ring|slash|th|tilde|uml|caron);~i', '$1', htmlentities($string, ENT_COMPAT, 'UTF-8'));
}
不工作的地方(不正确的匹配):我的意思是它没有在右侧给出预期的结果,
JÃŒrgen => Juergen
InÚs => Ines
它正在工作的地方(正确匹配):
Göran => Goran
Jørgen Ole => Jorgen
Jérôme => Jerome
可能是什么原因?怎么修?你有更好的办法处理所有案件吗?
答案 0 :(得分:4)
这可能就是你要找的东西
How to convert special characters to normal characters?
但请改用“utf-8”。
$text = iconv('utf-8', 'ascii//TRANSLIT', $text);
答案 1 :(得分:2)
简短回答
你有两个问题:
首先。这些名称没有重音。它们格式错误。
您似乎有一个UTF-8文件,但正在使用ISO-8559-1进行处理。例如,如果您告诉编辑器使用ISO-8859-1并使用UTF-8将文本复制粘贴到浏览器的文本区域中。然后,您将格式错误的名称保存在数据库中。我看到很多这样的问题都是由复制粘贴引起的。
如果名称格式正确,那么您可以解决第二个问题。让他们不高兴。对此有一个问题:How to convert special characters to normal characters?
答案很长(仅关注格式错误的重音字母)
为什么在需要Göran
?
Göran
让我们从Unicode开始:字母ö
是Unicode LATIN SMALL LETTER O WITH DIAERESIS
。其Unicode代码点为F6十六进制或分别为246十进制。请参阅Unicode link到Unicode数据库。
在ISO-8859-1中,0到255的代码点保持原样。带有分音符的小写字母o仅保存为一个字节:246。
UTF-8和ISO-8859-1将代码点0到127(也称为ASCII)视为相同。它们保持原样并保存为仅一个字节。它们在代码点128到255的处理方面有所不同.UTF-8可以编码整个Unicode代码点集,而ISO-8859-1只能处理前256个代码点。
那么,UTF-8对128以上代码点的作用是什么?随着代码点变得越来越大,代码点有一组交错的编码可能性。对于高达2047的代码点,两个字节就足够了。它们编码如下:(see this bit schema)
x xxxx xxxx xxxx => 110xxxxx 10xxxxxx
让我们用UTF-8中的diaresis编码小写字母o。这些位是:0 0000 1111 0110
并被编码为11000011 10110110
。这很好。
但是,这两个字节可能被误解为两个有效(!)ISO-8559-1字节。什么是11000011
(C3 hex)和10110110
(B6 hex)?我们来咨询an ISO-8859-1 table。 C3是Capital A代字号,B6是Paragraph符号。这两个标志都是有效的,没有软件可以通过查看位来检测这种误解。
明确需要知道名字的人。 Göran
不是名字。名称中间有一个大写字母,段落符号根本不是字母。可悲的是,这种误解并不止于此。由于所有字符都有效,因此可以对它们进行复制粘贴和重新渲染。在这个过程中,误解可以再次重复。让我们用Göran
来做这件事。我们已经误解了一次并且格式错误Göran
。字母Capital A,代字号和段落符号呈现为UTF-8中的两个字节每个(!),并被解释为gobbledygook的四个字节,类似于GÃÅ.ran
。
可怜的Jürgen!变音符ü
被误治了两次,我们有JÃŒrgen
。
我们这里的变音符号很糟糕。 OP甚至可能从他的客户那里得到这些数据。这件事发生在我身上:我得到了混合数据:格式良好,格式错误,一次,两次和三次在同一个文件中。这非常令人沮丧。