PHP中如何清理文件名粗体字符以解决MySQL 1366编码错误?
解决MySQL 1366字符错误的PHP字符清理方案
问题原因
你遇到的[HY000][1366]错误,是因为文件名中的粗体Unicode字母(属于数学符号范畴的变体字符,比如𝘽对应U+1D63D)不在当前数据库编码(通常是utf8mb3)的支持范围内,而你不想修改数据库编码,所以需要在存入前将这些特殊字符转换为普通ASCII字母。
实现方法
以下是两种可行的PHP处理方案,能将特殊变体字母转换为普通字母,得到符合需求的文件名:
方案一:字符映射数组替换
创建包含特殊变体字符与普通字符的映射表,通过strtr快速完成替换:
function cleanSpecialLetters($str) { // 粗体字母映射:键为特殊变体字符,值为对应普通ASCII字母 $charMap = [ '𝘼' => 'A', '𝘽' => 'B', '𝘾' => 'C', '𝘿' => 'D', '𝙀' => 'E', '𝙁' => 'F', '𝙂' => 'G', '𝙃' => 'H', '𝙄' => 'I', '𝙅' => 'J', '𝙆' => 'K', '𝙇' => 'L', '𝙈' => 'M', '𝙉' => 'N', '𝙊' => 'O', '𝙋' => 'P', '𝙌' => 'Q', '𝙍' => 'R', '𝙎' => 'S', '𝙏' => 'T', '𝙐' => 'U', '𝙑' => 'V', '𝙒' => 'W', '𝙓' => 'X', '𝙔' => 'Y', '𝙕' => 'Z', // 若需要处理小写粗体字母,可补充以下映射 // '𝙖' => 'a', '𝙗' => 'b', '𝙘' => 'c', ... ]; return strtr($str, $charMap); } // 测试使用 $dirtyFilename = '4 𝘽𝘼𝙉𝘿𝙀 𝘼𝙉𝙉𝙊𝙉𝘾𝙀 - TV.mp4'; $cleanFilename = cleanSpecialLetters($dirtyFilename); echo $cleanFilename; // 输出:4 BANDE ANNONCE - TV.mp4
方案二:正则+Unicode属性匹配(更通用)
利用PHP正则的Unicode属性匹配,自动识别所有数学变体字母,通过回调函数转换为普通字母:
function cleanMathVariantLetters($str) { return preg_replace_callback('/\p{Math}/u', function($matches) { $codePoint = mb_ord($matches[0], 'UTF-8'); // 转换粗体大写字母(U+1D63A 至 U+1D653) if ($codePoint >= 0x1D63A && $codePoint <= 0x1D653) { return chr($codePoint - 0x1D63A + ord('A')); } // 转换粗体小写字母(U+1D654 至 U+1D66D) elseif ($codePoint >= 0x1D654 && $codePoint <= 0x1D66D) { return chr($codePoint - 0x1D654 + ord('a')); } // 其他无法转换的字符保留原样 return $matches[0]; }, $str); } // 测试使用 $dirtyFilename = '4 𝘽𝘼𝙉𝘿𝙀 𝘼𝙉𝙉𝙊𝙉𝘾𝙀 - TV.mp4'; $cleanFilename = cleanMathVariantLetters($dirtyFilename); echo $cleanFilename; // 输出:4 BANDE ANNONCE - TV.mp4
注意事项
- 如果还有斜体、空心体等其他类型的变体字符,可以扩展映射表或正则判断逻辑。
- 确保PHP文件编码为UTF-8,避免处理过程中出现乱码。
- 转换后建议验证结果,确认所有特殊变体字符都被正确替换。
内容的提问来源于stack exchange,提问作者VaN
相关产品推荐
相关产品推荐

