网页中的编码问题,编码转换问题,以及file_get_contents

本文详细记录了处理编码问题的经验,包括如何正确获取网页内容及其编码方式,并解决了使用不同PHP函数获取相同网页内容时编码不一致的问题。通过实例分析了如何判断和转换网页编码,以及使用curl函数获取网页内容的高效性。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

最近遇到了很多关于编码的问题。总结一下,记录在此。

1.  

 $PageCode=curl_file_get_contents("http://www.12306.cn");
 echo $PageCode;

我的页面编码全是utf-8,看到铁道部的源文件编码方式也是utf-8(实际上是www.12306.cn/mormhweb/index.html的编码方式是utf-8,因为铁道部的首页跳转到了此页。),所以不用进行编码转换。

但结果输出总是乱码。原来铁道部的网站首页进行了跳转,下面是铁道部的首页的源码:

<html>
<head>
<title>
铁路客户服务中心
</title>
<head>
<script lang="JAVASCRIPT">
var url = location.host;
if(url=="www.12306.cn")
{
	window.location="/mormhweb/";
}
else
{

	if(url=="wap.12306.cn")
	{
		window.location="/mormhwap/";
	}
	else
	{
		alert("非法的地址,浏览器将关闭!");
		window.close();
	}
}


</script>
</html> 


首页的页面编码方式实际上是GBK,是我经过测试才知道的。在它的首页源文件中是看不到编码方式的。

最开始我是用

  

 if(preg_match("/charset=gb2312\"/",strtolower($PageCode))==1)
            $PageCode=mb_convert_encoding($PageCode,"UTF-8","gb2312");
      if(preg_match("/charset=gbk\"/",strtolower($PageCode))==1)
            $PageCode=mb_convert_encoding($PageCode,"UTF-8","gbk");

来进行编码判断并转换的,但有少数页面根本不行。因为页面上没有charset=gbk之类的,所以得通过其他方式进行编码判断。
下面有种方法可以直接判断字符串的编码是否为utf-8:

function is_utf8($liehuo_net) 
{ 
if (preg_match("/^([".chr(228)."-".chr(233)."]{1}[".chr(128)."-".chr(191)."]{1}[".chr(128)."-".chr(191)."]{1}){1}/",$liehuo_net) == true || preg_match("/([".chr(228)."-".chr(233)."]{1}[".chr(128)."-".chr(191)."]{1}[".chr(128)."-".chr(191)."]{1}){1}$/",$liehuo_net) == true || preg_match("/([".chr(228)."-".chr(233)."]{1}[".chr(128)."-".chr(191)."]{1}[".chr(128)."-".chr(191)."]{1}){2,}/",$liehuo_net) == true) 
{ 
return true; 
} 
else 
{ 
return false; 
}
}


于是可以这样进行编码判断并转换:

if(is_utf8($PageCode)!=1) 
{ 
$PageCode=mb_convert_encoding($PageCode,"UTF-8","GBK");
}

另外,在测试过程中,我把上面$PageCode=mb_convert_encoding($PageCode,"UTF-8","GBK");这句话改成$PageCode = iconv("UTF-8","gbk",$PageCode); 
结果是乱码。虽然iconv的执行效率比mb_convert_encoding高,但是通用性和稳定性没有mb_convert_encoding好,所以牺牲一点效率,来换取更稳定的效果。

2. 

$PageCode=file_get_contents("http://www.sohu.com");
$PageCode=mb_convert_encoding($PageCode,"UTF-8","GBK");
echo $PageCode;

因为搜狐的编码是GBK,而我的页面编码是utf-8,所以要进行编码转换。但结果还是乱码!我用各种编码方式来转换结果都是乱码。伤透了我的心。
后来在网上看到别人自己写了个类似linux下面的curl的函数:
function curl_file_get_contents($durl){
  $ch = curl_init();
  curl_setopt($ch, CURLOPT_URL, $durl);
  curl_setopt($ch, CURLOPT_TIMEOUT, 5);
  curl_setopt($ch, CURLOPT_USERAGENT, _USERAGENT_);
  curl_setopt($ch, CURLOPT_REFERER,_REFERER_);
  curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
  $r = curl_exec($ch);
  curl_close($ch);
  return $r;
}


于是我用这个函数试了一下$PageCode=curl_file_get_contents("http://www.sohu.com");,结果OK!
让我很不明白的是,为什么用php的函数file_get_contents得到的搜狐的首页源文件编码总是有问题呢?而用curl方式得到的就木有问题?
问题算是解决了,但是有些地方还不是很明白,不知道是怎么回事,权且先记下来,以后再慢慢深究。


`file_get_contents('php://input')` 是 PHP 中一个常用的函数,用于读取原始的 HTTP 请求体数据。这个函数在处理 POST 请求时特别有用,尤其是当请求的数据不是表单编码(如 `application/x-www-form-urlencoded` 或 `multipart/form-data`)时,比如 JSON 或 XML 数据。 ### 使用场景 1. **处理 JSON 数据**:当客户端发送 JSON 格式的数据时,可以通过 `file_get_contents('php://input')` 获取原始的 JSON 字符串,然后使用 `json_decode` 将其转换为 PHP 对象或数组。 2. **处理 XML 数据**:类似地,当客户端发送 XML 格式的数据时,可以通过这个函数获取原始的 XML 字符串,然后使用 `simplexml_load_string` 或其他 XML 解析库进行解析。 3. **处理二进制数据**:当需要处理上传的二进制数据(如文件上传)时,也可以使用这个函数获取原始的二进制数据。 ### 示例代码 ```php <?php // 获取原始的 HTTP 请求体数据 $rawData = file_get_contents('php://input'); // 假设客户端发送的是 JSON 数据 $data = json_decode($rawData, true); if ($data === null) { // 处理 JSON 解码错误 http_response_code(400); echo json_encode(['error' => 'Invalid JSON']); exit; } // 处理数据 echo json_encode(['status' => 'success', 'data' => $data]); ?> ``` ### 优点 - **灵活性**:可以处理各种格式的数据,而不仅仅是表单数据。 - **性能**:直接读取原始数据,避免了 PHP 自动解析表单数据的开销。 ### 注意事项 - **数据长度**:对于非常大的请求体,读取数据可能会消耗大量内存,需要注意数据长度。 - **安全性**:确保对读取到的数据进行适当的验证和消毒,以防止安全漏洞。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值