`
ice123456
  • 浏览: 26913 次
  • 性别: Icon_minigender_1
  • 来自: 武汉
文章分类
社区版块
存档分类
最新评论

抓出问天网的城市天气

阅读更多
package com.ice.weather.util;

import java.io.BufferedReader;
import java.io.InputStreamReader;

import java.net.URL;

import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

import java.text.SimpleDateFormat;

import com.ice.weather.bean.Weather;

public class OpenUrl {
	@SuppressWarnings("deprecation")
	public static void main(String[] args) throws Exception{
		OpenUrl openUrl = new OpenUrl();
		List<Weather> list = openUrl.getWeatherByUrl("http://weather.tq121.com.cn/detail.php?city=武汉");
		for (Weather w : list) {
			System.out.println("时间:" + w.getDate().toLocaleString());
			System.out.println("天气信息:" + w.getWeatherInfo());
			System.out.println("温度:" + w.getTemperature());
			System.out.println("风速信息:" + w.getWindInfo());
		}
	}
	
	/**
	 * 根据连接抓出5天天气
	 */
	public List<Weather> getWeatherByUrl(String url){
		try {
			String content = getContent(url);
			List<Weather> list = getWeathers(content);
			list.addAll(getWeathersBack(content));
			return list;
		} catch (Exception e) {
			System.out.println(e);
			return new ArrayList<Weather>();
		}
	}

	/**
	 * 根据连接地址抓出页面内容
	 * @param 根据一个连接地址
	 * @return 页面内容
	 */
	private String getContent(String strUrl){
		try {
			URL url = new URL(strUrl);
			BufferedReader br = new BufferedReader(new InputStreamReader(url.openStream()));
			String s = "";
			StringBuffer sb=new StringBuffer();
			while((s = br.readLine())!=null)
				sb.append(s+"\r\n");
			br.close();
			return sb.toString();
		} catch(Exception e) {
			return "error open url" + strUrl;
		}
	}

	/**
	 * 取当前3天内的天气情况
	 * content 为页面内容
	 */
	private List<Weather> getWeathers(String content) throws Exception {
		List<Weather> weatherList = new ArrayList<Weather>();
		int o = 6;
		String[] s = analysis("<td width=\"215\" align=\"center\" valign=\"middle\"><span class=\"big-cn\">(.*?)</span></td>", content , o);
		Weather weather;
		for (int i = 0; i < o; i += 2) {
			weather = new Weather();
			weather.setDate(conversionDate(s[i]));
			weather.setTemperature(s[i + 1]);
			weatherList.add(weather);
		}
		s = analysis("align=\"center\" valign=\"top\"><img src=\"../images/a(.*?).gif\" width=\"70\" height=\"65\"></td>" , content , o);
		s = ConversionWeather(s);
		o = 3;
		for (int i = 0; i < o; i++) 
			weatherList.get(i).setWeatherInfo(s[i]);
		s = analysis("<td width=\"215\" align=\"center\" valign=\"middle\"><span class=\"cn\">(.*?)</span></td>", content , o);
		for (int i = 0; i < o; i++)
			weatherList.get(i).setWindInfo(s[i]);
		return weatherList;
	}

	private List<Weather> getWeathersBack(String content) throws Exception {
		List<Weather> weatherList = new ArrayList<Weather>();
		int o = 2;
		String[] s = analysis("<td width=\"121\"><span class=\"cn\">(.*?)</span></td>" , content , o);
		Weather weather;
		for (int i = 0; i < o; i++) {
			weather = new Weather();
			weather.setDate(conversionDate(s[i]));
			weatherList.add(weather);
		}
		
		s = analysis("<td width=\"86\" class=\"cn\"><span class=\"wendu\">(.*?)</span></td>" , content , o);
		for (int i = 0; i < o; i++)
			weatherList.get(i).setTemperature(s[i]);
		
		s = analysis("<td width=\"157\"><span class=\"cn\">(.*?)</span></td>" , content , o);
		for (int i = 0; i < o; i++)
			weatherList.get(i).setWindInfo(s[i]);
	
		s = analysis("<img src=\"../images/b(.*?).gif\" width=\"50\" height=\"46\"></td>" , content , o*2);
		s = ConversionWeather(s);
		for (int i = 0; i < o; i++)
			weatherList.get(i).setWeatherInfo(s[i]);
		
		return weatherList;
	}

	/**
	 * 根据爬出到日期转换当前时间
	 */
	private Date conversionDate(String date) throws Exception {
		SimpleDateFormat dateformat = new SimpleDateFormat("MM月dd日");
		Date d = dateformat.parse(date);
		Calendar c = Calendar.getInstance();
		c.setTime(d);
		c.set(Calendar.YEAR, Calendar.getInstance().get(Calendar.YEAR));
		return c.getTime();
	}

	/**
	 * 根据页面内容和正则表达式来分析页面,得到分析结果
	 * @param pattern 正则表达式
	 * @param match 页面内容
	 * @return content 结果
	 */
	private String[] analysis(String pattern, String match , int i) {
		Pattern sp = Pattern.compile(pattern);
	    Matcher matcher = sp.matcher(match);
	    String[] content = new String[i];
	    for (int i1 = 0; matcher.find(); i1++)
	    	content[i1] = matcher.group(1).trim();
	    return content;
	}

	/**
	 * 转换天气情况
	 * @param s 图片信息
	 * @return 天气情况
	 */
	private String[] ConversionWeather(String s[]) {
		String[] s1 = {"晴天", "多云", "阴", "阵雨", "雷阵雨", "雷阵雨并伴有冰雹", "雨加雪", "小雨", "中雨", "大雨", "暴雨", "大暴雨", "特大暴雨", "阵雪", "小雪", "中雪", "大雪", "暴雪", "雾", "冻雨", "沙尘暴", "小雨-中雨", "中雨-大雨", "大雨-暴雨", "暴雨-大暴雨", "大暴雨-特大暴雨", "小雪-中雪", "中雪-大雪", "大雪-暴雪", "浮尘", "扬沙", "强沙尘暴"};
		String[] s2 = new String[s.length/2];
		int i1 = 0;
		for (int i = 0; i < s.length; i += 2){
			if (s[i].trim().equals(s[i+1].trim()))
				s2[i1] = s1[Integer.parseInt(s[i])];
			else
				s2[i1] = s1[Integer.parseInt(s[i])] + "转" + s1[Integer.parseInt(s[i+1])];
			i1++;
		}
		return s2;
	}
}


package com.ice.weather.bean;

import java.util.Date;

public class Weather {
	private Date date;

	private String temperature;

	private String weatherInfo;

	private String windInfo;

	public Date getDate() {
		return date;
	}

	public void setDate(Date date) {
		this.date = date;
	}

	public String getTemperature() {
		return temperature;
	}

	public void setTemperature(String temperature) {
		this.temperature = temperature;
	}

	public String getWeatherInfo() {
		return weatherInfo;
	}

	public void setWeatherInfo(String weatherInfo) {
		this.weatherInfo = weatherInfo;
	}

	public String getWindInfo() {
		return windInfo;
	}

	public void setWindInfo(String windInfo) {
		this.windInfo = windInfo;
	}
}

最新修改过了··代码跟简洁...下午应该做一个js版的
分享到:
评论
22 楼 Julian 2007-10-25  
说说我的方法:我是抓的新浪的天气,抓回来后提供webservice。
webservice内有一个60分钟缓存。
本来打算作一个外部服务监控程序,就是对天气预报的提供商(新浪)进行定时监控,发现我的天气预报webservice歇菜了就马上给我发个mail.这时候先让webservice提供缓存里面的天气信息(1天的信息),然后在1天内修复这个文天。
目前看来大型网站的天气预报格式变化比较慢,至少6个月以上。
21 楼 ice123456 2007-10-25  
swiage 写道
我觉得 analysis 函数的返回值如果定义为 Vector 类型,使用起来可以更灵活;
private Vector search(String pattern, String match){  
        Pattern sp = Pattern.compile(pattern);  
        Matcher matcher = sp.matcher(match);  
        Vector myvector = new Vector();
        while(matcher.find()){  
            myvector.add(matcher.group(1));  
        }       
        return myvector;  
    }  这样做我们就不必预先知道搜索结果的数量了。

不是我不想这样做 只是页面的布局是这样的 
20 楼 swiage 2007-10-24  
我觉得 analysis 函数的返回值如果定义为 Vector 类型,使用起来可以更灵活;
private Vector search(String pattern, String match){  
        Pattern sp = Pattern.compile(pattern);  
        Matcher matcher = sp.matcher(match);  
        Vector myvector = new Vector();
        while(matcher.find()){  
            myvector.add(matcher.group(1));  
        }       
        return myvector;  
    }  这样做我们就不必预先知道搜索结果的数量了。
19 楼 jarwang 2007-10-21  
如下图:


还是我不会运行.....
18 楼 ice123456 2007-10-20  
gigix 写道
ice123456 写道
ladofwind 写道
这样太危险了吧,那边页面格式一变你这边程序就歇了,
我们以前用的是一个免费提供天气信息的web services服务,
直接在这边调用各种服务,能得到各种天气信息,
信息你在本地怎么处理都可以,包括显示方式啊什么的


难到问天网有提供天气信息的web services服务吗??  在国内提供天气信息的基本没有web services服务
不要跟我说yahoo的, yahoo提供的是国外的web services,对中国的天气支持不是非常好,它有些信息都不正确

呵呵,那正好
你把这个信息清扫一下,用web services提供出来,不就方便别人了


有道理.
17 楼 gigix 2007-10-19  
ice123456 写道
ladofwind 写道
这样太危险了吧,那边页面格式一变你这边程序就歇了,
我们以前用的是一个免费提供天气信息的web services服务,
直接在这边调用各种服务,能得到各种天气信息,
信息你在本地怎么处理都可以,包括显示方式啊什么的


难到问天网有提供天气信息的web services服务吗??  在国内提供天气信息的基本没有web services服务
不要跟我说yahoo的, yahoo提供的是国外的web services,对中国的天气支持不是非常好,它有些信息都不正确

呵呵,那正好
你把这个信息清扫一下,用web services提供出来,不就方便别人了
16 楼 fkpwolf 2007-10-19  
天气好像有通用的接口吧
比如mac osx上面的wigdet
vista上面也有类似的
15 楼 ice123456 2007-10-19  
jarwang 写道
代码无法运行。

???
  怎么可能
14 楼 jarwang 2007-10-18  
代码无法运行。
13 楼 kenees 2007-10-18  
ladofwind 写道
这样太危险了吧,那边页面格式一变你这边程序就歇了,
我们以前用的是一个免费提供天气信息的web services服务,
直接在这边调用各种服务,能得到各种天气信息,
信息你在本地怎么处理都可以,包括显示方式啊什么的
12 楼 belivexiaoqi 2007-10-18  
感觉code 有点乱,weather类构造的有点问题,

构造的weather类应该只有四个属性:date,temperature,weather,wind。

取哪天的天气,返回哪天的weather就ok了,不要一直不停的set,get.....看了太不舒服了。。

11 楼 ice123456 2007-10-18  
comliu 写道
除了用正则表达式,也可以采用Dom4j的XPath功能进行检索。

Dom4j??  没有用过  介绍下?
10 楼 comliu 2007-10-18  
除了用正则表达式,也可以采用Dom4j的XPath功能进行检索。
9 楼 ice123456 2007-10-18  
ladofwind 写道
这样太危险了吧,那边页面格式一变你这边程序就歇了,
我们以前用的是一个免费提供天气信息的web services服务,
直接在这边调用各种服务,能得到各种天气信息,
信息你在本地怎么处理都可以,包括显示方式啊什么的


难到问天网有提供天气信息的web services服务吗??  在国内提供天气信息的基本没有web services服务
不要跟我说yahoo的, yahoo提供的是国外的web services,对中国的天气支持不是非常好,它有些信息都不正确
8 楼 eric chang 2007-10-17  
ladofwind 写道
这样太危险了吧,那边页面格式一变你这边程序就歇了,
我们以前用的是一个免费提供天气信息的web services服务,
直接在这边调用各种服务,能得到各种天气信息,
信息你在本地怎么处理都可以,包括显示方式啊什么的
同意楼上的意见,这样的代码确实太不好了
7 楼 ladofwind 2007-10-17  
这样太危险了吧,那边页面格式一变你这边程序就歇了,
我们以前用的是一个免费提供天气信息的web services服务,
直接在这边调用各种服务,能得到各种天气信息,
信息你在本地怎么处理都可以,包括显示方式啊什么的
6 楼 tomgreenintel 2007-10-17  
如果对方把get方式给屏蔽掉。你怎么弄呢?没有根本灵活实现啊
5 楼 InnocentBoy 2007-10-17  
不过问天网不用登录的,哈哈!
4 楼 ice123456 2007-10-17  
Michael.zhl 写道
这样获得html是不是不太灵活?比如对方网站要求登陆,验证cookie

这方面到没有想过.... 谢谢你的意见
3 楼 cqx2004 2007-10-17  
有意思。。

相关推荐

Global site tag (gtag.js) - Google Analytics