$ _POST将从utf-8转换为öü等

时间:2012-01-25 12:27:35

标签: php encoding utf-8 character-encoding mojibake

我是新来的,所以如果我做错了什么,我道歉。

我有一个表单,用于将用户输入提交到另一个页面。用户需要键入ä,ö,é等...我已将所有以下内容放在文档中:

<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
header('Content-Type:text/html; charset=UTF-8');
<form action="whatever.php" accept-charset="UTF-8">

我甚至尝试过:

ini_set('default_charset', 'UTF-8');

当其他页面加载时,我需要检查用户输入的内容如下:

if ( $_POST['field'] == $check ) {
  ...
}

但如果他输入类似'München'的东西,PHP会将'München'与'München'进行比较,即使它应该也不会触发TRUE。由于它在任何地方都指定了UTF-8,我猜测服务器正在转换为其他东西(我在另一个线程上读取的Windows-1252),因为它不支持或未配置为UTF-8。我在加载到生产之前在本地服务器上使用Apache;我没有改变(也不知道如何)任何默认设置。我一直在研究Windows 7,使用Notepad ++进行编辑,用ANSI输入我的文件。如果我bin2hex('München')我得到'4dc3bc6e6368656e'。

如果我echo $_POST['field'];它正确显示'München'。

我到处研究解释,我发现我应该包括那些我已经拥有的标签/标题。

非常感谢任何帮助。

5 个答案:

答案 0 :(得分:14)

你面临着许多不同的问题,让我们从最简单的问题开始。

问题1)您说echo $_POST['field'];会正确显示吗? “显示”是什么意思?它可以在两种情况下正确显示:

  • 该字段为UTF-8且您的页面已声明为UTF-8,浏览器将其显示为UTF-8或
  • 该字段位于Latin-1,浏览器已决定(通过自动检测启发式方法)您的网页为Latin-1。

因此,echo $_POST['field'];正确的事实告诉你什么。

问题2)您正在使用

<meta http-equiv="Content-Type" content="text/html; charset=UTF-8"/>
header('Content-Type:text/html; charset=UTF-8');

这是PHP代码吗?如果是,则会出错,因为必须在发送任何字节之前设置标头。如果这样做,您将不会设置Content-Type标头,PHP应该生成警告。

问题3)您正在使用

<form action="whatever.php" accept-charset="UTF-8">

如果某些浏览器(IE,大多数)可以强制要以ASCII或ISO Latin-1发送的数据,则忽略accept-charset。所以数据将是UTF-8并声明为ISO Latin-1或ISO Latin-1并作为ISO Latin-1发送(但第二种情况不是你的情况)。

请查看https://stackoverflow.com/a/8547004/449288,了解如何解决此问题。

问题4)你在比较哪些字符串?例如,如果你有

$city = "München"
$_POST['city'] == $city

此代码的结果取决于PHP文件的编码。如果文件以ISO Latin-1编码且$_POST正确包含UTF-8数据,则==将比较不同的字节并返回false。

答案 1 :(得分:3)

另一个可能有用的解决方案是在Apache中,您可以在配置文件(httpd.conf)或.htacess中放置一个名为AddDefaultCharset的指令。它看起来像这样:

AddDefaultCharset utf-8

http://httpd.apache.org/docs/2.0/mod/core.html#adddefaultcharset

这将覆盖任何其他默认字符集。

答案 2 :(得分:3)

我在php.ini文件中更改了“mbstring.detect_order = pass”并且我工作了

答案 3 :(得分:0)

我在表单和文件中多次使用Unicode字符。到目前为止我没有任何问题。 尝试执行这些步骤并检查结果:

  1. 从HTML表单代码中删除header('Content-Type:text/html; charset=UTF-8');
  2. 使用您的表单,就像<form action="whatever.php">没有accept-charset="UTF-8"一样。 (最好在表单标签中插入发送数据的方法。)
  3. 在目标网页(whatever.php)中,再次在<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">代码中插入<head>
  4. 我总是像我在这里提到的那样完成我的项目,我对Unicode字符串没有任何问题。

答案 4 :(得分:0)

这是由于PHP文件的字符编码。

硬编码的München与源文件的字符编码一起存储,在本例中为ANSI,并且当该值与{{{0}中提供的UTF-8编码值进行比较时1}}变量,两者将很自然地不同。

您的问题的解决方案之一是:

  1. 使用与源文件相同的编码来处理和处理内容,在这种情况下可能是$_POST
    • 对于初学者,这包括在提供HTML数据时将windows-1252更改为content="text/html; charset=UTF-8"
  2. 避免所有可能受content="text/html; charset=windows-1252"UTF-8之间字符编码问题影响的硬编码值,或多或少只有 包含英文字母和数字的硬编码值。
    • 必须从源中读取任何windows-1252值,以确保它们UTF-8编码(例如,数据库设置为使用UTF-8作为存储编码以及连接编码)
  3. UTF-8中换行所有硬编码的作业,例如utf8_encode()
  4. 将源文件的编码更改为$value = utf8_encode ('München');
    • 这可以通过多种方式实现,一个体面的文本编辑器可以做到这一点,或者可以使用优秀的libiconv,尤其是批量处理。
  5. 解决方案1或4都是我的首选解决方案,特别是如果项目涉及多个人。

    作为旁注,一些文字编辑(特别是UTF-8)可以选择使用Notepad++UTF-8UTF-8 without BOM(字节顺序标记)在BOM中毫无意义,并且在PHP中编写标头时会出现问题(最常见的是在进行重定向时)。这是因为UTF-8位于初始BOM的正前方,导致服务器发送<?php,就像前面的任何其他字符一样。不同之处在于您会在前面注明一个角色,但不会显示BOM 经验法则:始终使用没有BOM的UTF-8。