一个网页抓取的类支持get+post+cookie存储

以前做个贴吧发帖机,然后设定的的是发一贴需登录一次,最后账号被禁用了。最后就改了下程序,登录一次保存cookie信息,下次再发帖就不用登陆了。

[php]
<?php
class httpconnector {
private $curl;
private $cookie;
private $kv;
function __construct(){
$this->kv = new SaeKV();
$this->kv->init();
if($data=$this->kv->get("cookie"))
$this->cookie=$data;

}
public function get($url) {
$this->curl = curl_init();
curl_setopt($this->curl, CURLOPT_URL, $url);
curl_setopt($this->curl, CURLOPT_HEADER, 1);
curl_setopt($this->curl, CURLOPT_USERAGENT, "Mozilla/4.0 (compatible; MSIE 5.01; Windows NT 5.0)");
curl_setopt($this->curl, CURLOPT_COOKIE, $this->cookie);
curl_setopt($this->curl, CURLOPT_RETURNTRANSFER, 1);
$data = curl_exec($this->curl);
curl_close($this->curl);
preg_match_all("/Set-Cookie:(.*?);/", $data, $match, PREG_SET_ORDER);
foreach ($match as $r) {
if ($this->cookie != ”) {
$this->cookie = $this->cookie . ‘;’;
}
if (isset($r[1])) {
$this->cookie .= trim(str_replace("rn", "", $r[1]));
}
}
$this->kv->set("cookie",$this->cookie);
return $data;

}
public function post($url, $params) {
$this->curl = curl_init();
curl_setopt($this->curl, CURLOPT_URL, $url);
curl_setopt($this->curl, CURLOPT_HEADER, 1);
curl_setopt($this->curl, CURLOPT_COOKIE, $this->cookie);
curl_setopt($this->curl, CURLOPT_POST, 1);
curl_setopt($this->curl, CURLOPT_USERAGENT, "Mozilla/4.0 (compatible; MSIE 5.01; Windows NT 5.0)");
curl_setopt($this->curl, CURLOPT_POSTFIELDS, $params);
curl_setopt($this->curl, CURLOPT_RETURNTRANSFER, 1);
$data = curl_exec($this->curl);
curl_close($this->curl);
preg_match_all("/Set-Cookie:(.*?);/", $data, $match, PREG_SET_ORDER);
foreach ($match as $r) {
if ($this->cookie != ”) {
$this->cookie = $this->cookie . ‘;’;
}
if (isset($r[1])) {
$this->cookie .= trim(str_replace("rn", "", $r[1]));
}
}
$this->kv->set("cookie",$this->cookie);
return $data;

}
}
?>
[/php]

加载进度条

[html]
<style type="text/css">
body{
padding: 20px;
font-size: 14px;
}
#progressbar{
width: 278px;
}
#progressbar .border{
border: 1px solid #777;
width: 276px;
height: 13px;
padding: 1px;
}
#progressbar .bar{
background-color: #73c944;
width: 50%;
height: 13px;
overflow: hidden;
}
#progressbar .desc{
text-align: center;
font-size: 12px;
line-height: 24px;
}
</style>
<div id="progressbar">
<div class="border">
<div class="bar">&#160;</div>
</div>
<div class="desc">
正在加载…
</div>
</div>

<p>loading 将在 10s 后结束。</p>

<script type="text/javascript">
<!–
var loading = function(){
var ct = document.getElementById("progressbar"),
desc = ct.getElementsByTagName("div"),
idx = 0, time = 500, bar = desc[1], desc = desc[2];
bar.setValue = function(n){
this.style.width = n + "%"; };
void function(){
bar.setValue(idx += (100 – idx) * .2);
timer = setTimeout(arguments.callee, time += 100);
}();
return {
remove: function(){
clearTimeout(timer);
desc.innerHTML = "加载完成";
bar.setValue(100);
setTimeout(function(){
ct.parentNode.removeChild(ct);
}, 500);
}
};
}();

setTimeout(loading.remove, 10000);
//–>
</script>
[/html]

如何高效开发一个完整的网站

一个完整的网站包括两部分:1.业务逻辑2.界面,专业点的讲即M+V+C , M是model即模型存放网站业务逻辑,V是view 即视图,也是网站界面,C是control顾名思义联系model和view,控制显示。但是很多人在开发网站时M和C分的不是很清,我本人也经常犯这种错误,那么这样做有什么坏处呢,后面讲。

本文主要讲如何高效的开发一个完整的网站。先将业务逻辑的编写,首先,你要确定网站的需求,需要有哪些功能,考虑哪些功能需要在不同的场景多次使用(这样的场景毫无疑问要放在M中,为了维护方便保持、保持一致性),然后设计数据库,但是这时候设计只是简要的设计,不必苦思冥想,因为在你真正开始做的时候,就会发现,以前的设计会有缺陷,然后就一边改一边做。设计好数据库结构时开始写代码了,首先你要先写后台那部分,后台的每个功都可以概括如下:数据的增、删、改、查,因此如果针对每个数据表写SQL语句会很痛苦,所以要借助开发框架,国内比较出色的是Thinphp,我看了开发文档,不是多好,推荐国外的zendframework 和YII,这两个是世界上最有名的两个,功能极其强大,唯一的不足是,要阅读英文文档去学习,中文的大多是过时的。好了,借助框架,增删改查数据可以简化到极致,开发极其方便。后台写完了,就开始写前台了,前台主要是呈现数据传递信息,最好做到简单,并快速传递访客想获得数据,因此,前台的设计要好好考虑,当然前台的数据一般只设计查和增两个功能,查询是常见的,增主要是加些评论神马的。

后台写完了,你会发现虽然功能实现了,但是有点丑陋。所以,也是没法交付使用的,那我们开始写界面代码。以前我认为写界面靠ps,而后做了几个项目后,我发现我PS一点都不会,也可以设计的很好,这也主要借助了框架,我用的是外国的twitter工程师开发的bootstrap框架,有点遗憾的是它不支持IE,在IE下显示效果极差,幸运的是他们提供了一个解决在IE下显示不好的解决方案,详情见https://github.com/empowering-communities/Bootstrap-IE6 英文的,不过很简单,一读就明白了。到此,一个网站开发完了。

至于效率,我用数据说话,我这学期做了四个项目。第一个项目完全不用框架写了二十天,第四个项目全靠框架,功能差不多(比第一个简单点),只用了三天。但是第四个效果、性能、加载速度要远优于第一个。

抓取最近八天天气(非利用接口,直接从网站提取)

[php]
<?php
/*
*特别注意,第一天没有最高气温数据,第八天没有最低气温数据
*注意对数字进行过滤时不要忘记对负号进行判断
*对风力过滤时要考虑到3-5级这种格式
*/
class weatherfetch{
private $f;
function getNum($string) {
$tmpstr = ”;
$strlen = strlen($string);
for($i=0; $i<$strlen; $i++) {
$str=substr($string, $i, 1);
$str1=trim($str);
if(is_numeric($str1)){
$tmpstr.=$str1+0;

}
if($str1=="-"&&is_numeric(substr($string, $i-1, 1))){
$tmpstr.= $str1;
}

}
return $tmpstr;
}
function __construct(){
$this->f= new SaeFetchurl();

}
function getChineseNum($string){
$tmpstr = ”;
$arr = array(1,2,3,4,5,6,7,8,9,0);
$strlen = strlen($string);
for($i=0; $i<$strlen; $i++) {

$str=substr($string, $i, 1);

$str1=trim($str);
if( ord($str)>0xA0 ){

$tmpstr.= substr($string, $i, 3);

$i = $i+2;

}

if(is_numeric($str1)){

$tmpstr.= $str1;

}
if($str1=="-"&&is_numeric(substr($string, $i-1, 1))&&is_numeric(substr($string, $i+1, 1))){
$tmpstr.= $str1;
}

}

return $tmpstr;

}
function getChinese($string,$encode="GBK") {
switch($encode){
case "GBK" :$codelength=2;break;
case "GB2312" :$codelength=3;break;
case "UTF-8" :$codelength=3;break;
case "UTF-16" :$codelength=4;break;

}
$tmpstr = ”;
$arr = array(1,2,3,4,5,6,7,8,9,0);
$strlen = strlen($string);
for($i=0; $i<$strlen; $i++) {
$str=substr($string, $i, 1);
$str1=trim($str);
if( ord($str)>0xA0 ){
$tmpstr.= substr($string, $i, $codelength);
$i = $i+$codelength-1;
}

}
return $tmpstr;
}
function get($cityid){
$url="http://www.weather.com.cn/weather/".$cityid.".shtml";
$data=$this->f->fetch($url);

$sun=explode(‘<div class="weatherTopright">’,$data);
$sun=explode("<dl>",$sun[1]);
$sun=explode("</dl>",$sun[1]);
$sun=explode("</strong>",$sun[0]);
$sunrise=strlen($sun[0]);
$sunrise=substr($sun[0],$sunrise-5);//日出时间
$sunset=strlen($sun[1]);
$sunset=substr($sun[1],$sunset-5);//日落时间
$sunhour=substr($sunset,0,2)-substr($sunrise,0,2);
$sunminute=$sunhour*60+substr($sunset,-2)-substr($sunrise,-2);//日照时间
$yubao=explode(‘class="yuBaoTable"’,$data);
$num=count($yubao);
$tl=array();
$th=array();
$fx=array();
$fl=array();
$weather=array();
//第一天
$tr=explode("</tr>",$yubao[1]);
$td=explode("</td>",$tr[0]);
$weather[]=$this->getChinese($td[3],"UTF-8");//晚上天气
$fx[]=$this->getChinese($td[5],"UTF-8");//晚上风向
$fl[]=substr($this->getChineseNum($td[6],"UTF-8"),5);//晚上风力
$tltemp=explode("<strong>",$td[4]);//最低气温
$tl[]=$this->getNum($tltemp[1]);
//从第二天到第七天
for($i=2;$i<$num-1;$i++){
$tr=explode("</tr>",$yubao[$i]);
$td=explode("</td>",$tr[0]);
$weather[]=$this->getChinese($td[3],"UTF-8");//白天天气
$fx[]=$this->getChinese($td[5],"UTF-8");//白天风向
$fltemp=substr($this->getChineseNum($td[6],"UTF-8"),5);
$fl[]=$fltemp;//白天风力
$thtemp=explode("<strong>",$td[4]);
$th[]=$this->getNum($thtemp[1]);//最高气温
$td=explode("</td>",$tr[1]);
$tltemp=explode("<strong>",$td[3]);
$tl[]=$this->getNum($tltemp[1]);//最低气温

}
//第八天
$tr=explode("</tr>",$yubao[$num-1]);
$td=explode("</td>",$tr[0]);
$weather[]=$this->getChinese($td[3],"UTF-8");//白天天气
$fx[]=$this->getChinese($td[5],"UTF-8");//白天风向
$fl[]=substr($this->getChineseNum($td[6],"UTF-8"),5);//白天风力
$thtemp=explode("<strong>",$td[4]);
$th[]=$this->getNum($thtemp[1]);//最高气温
if(count($weather)==8){
return array("weather"=>$weather,"tl"=>$tl,"th"=>$th,"fx"=>$fx,"fl"=>$fl,"sunset"=>$sunset,"sunrise"=>$sunrise,"sunminute"=>$sunminute);
}else{
return 1;

}
}
function getday1($cityid){
$url="http://www.weather.com.cn/weather/".$cityid.".shtml";
$data=$this->f->fetch($url);
$yubao=explode(‘class="yuBaoTable"’,$data);
$tr=explode("</tr>",$yubao[1]);
$td=explode("</td>",$tr[0]);
$thtemp=explode("<strong>",$td[4]);
return $this->getNum($thtemp[1]);

}
}
[/php]