如何在PHP中“去除UTF8字符中的变音符号”?

4
我需要在PHP中复制MySQL的utf8_general_ci排序规则的行为。严格来说,我需要检测什么应该被认为是不同的,什么应该被认为是相同的。大小写无关的部分很容易。问题在于utf_general_ci将带变音符号和不带变音符号的字符视为相等:e = è = é等等。要复制该比较,我需要一种方法来替换è -> e、é -> e。
我想到的方法是:
echo iconv("utf-8", "ascii//TRANSLIT", "é");

一个问题是,iconv 的行为因当前语言环境而异,这会导致问题。

另一个问题是输入可能包含不应该被剥离或导致 PHP 注意的西里尔字母。

echo iconv("utf-8", "ascii//TRANSLIT", "дом");

是否有解决方案,还是我需要手动创建每个带附加符号的字符到没有附加符号的字符的映射?


请退一步并解释为什么您需要去除重音符号以及为什么您必须在PHP中执行此操作。 - Rick James
我需要批量插入一些值,并且必须确保它们都不会与数据库中已有的值冲突。 - Kalmar
2个回答

5

intl的Transliterator能够让您定义更为深入的音译规则。关于音译规则的完整文档可以在icu-project.org上找到。

$tests = [ "é", "дом" ];

$tl = Transliterator::create('Latin-ASCII;');
foreach($tests as $str) {
    var_dump(
        $tl->transliterate($str)
    );
}

输出:

string(1) "e"
string(6) "дом"

0
目标是“防止表中已存在的冲突值”?并且应该允许带有不同重音符号和非重音符号的重音字母共存?然后更改导致冲突的PRIMARY(或UNIQUE)键的排序规则。
任何..._bin COLLATION都将允许eé共存(在插入期间不发生冲突),因为它们被视为不同。
您是否需要...general_ci出于其他原因?如果是,请说明原因。如果没有,请使用ALTER TABLE更改COLLATION。我认为不需要PHP代码。

不,重音字母不应该与非重音字母共存。表中有utf8_general_ci,并且它将保留下来。为了简单起见,我们称之为业务需求。 因此,如果表中有“mere”,并且我尝试插入“mére”,我会收到DB错误。特别是如果我进行批量插入,则处理DB错误很麻烦,因此我想提前检测此类错误。因此在PHP中。 - Kalmar
矛盾:追求简单与为了绕过它而倒立。 - Rick James
你一直在误引用我的话或断章取义。你没有理解“比较的复制”和“业务需求”。这是在恶意挑衅,而不是帮助。PLONK - Kalmar

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接