[java] 汇率换算器实现(3)
[java] 汇率换算器实现(3)
[java] 汇率换算器实现(3)
Table of Contents
2 前言
在上一篇文章中, 我们充分了解了正则表达式的使用细则. 那么此处就结合java.util.regex库的使用, 实现HtmlTableParse类, 用于提取网页中table的内容.
3 提取简单表单信息
html表格的示例如下:
<table border="1">
<tr>
<th>Month</th>
<th>Savings</th>
</tr>
<tr>
<td>January</td>
<td>$100</td>
</tr>
</table>
将代码合并为一行后得:
<table border="1"><tr><th>Month</th><th>Savings</th></tr><tr><td>January</td><td>$100</td></tr></table>
针对上面一行书写相关的正则表达式, 获取表单中的内容:
<table.*?>((<tr>.*?</tr>)+?)</table>
这样 $1 就对应着 <tr><th>Month</th><th>Savings</th></tr><tr><td>January</td><td>$100</td></tr> , 接着对匹配后的结果再次进行处理, 使用得正则表达式为:
<tr>(.*?)</tr>
如此, 匹配得到每一行的内容, 如: $1 = <th>Month</th><th>Savings</th>, 接着再使用正则表达式:
<th>(.*?)</th>
就能够得到不同元素, 如:Month, Savings
3.1 Java正则表达式实现简单表单提取
import java.util.regex.*;
public class HtmlTable {
public static void main(String[] args) {
// 目标
String target = "<table border=\"1\"><tr><th>Month</th><th>Savings</th></tr><tr><td>January</td><td>$100</td></tr></table>";
// 正则表达式
String regexTable = "<table.*?>((<tr>.*?</tr>)+?)</table>";
String regexRow = "<tr>(.*?)</tr>";
String regexEle = "(?:<th>|<td>)(.*?)(?:</th>|</td>)";
Pattern r = Pattern.compile(regexTable);
// 表单的匹配
Matcher mTable = r.matcher(target);
while (mTable.find()) {
String strRow = mTable.group(1);
System.out.println("Row: "+strRow);
// 表单中每一行得匹配
Matcher mRow = Pattern.compile(regexRow).matcher(strRow);
while (mRow.find()) {
String strEle = mRow.group(1);
System.out.println("\tTh or td: " + strEle);
// 每一行中每个元素得匹配
Matcher mEle = Pattern.compile(regexEle).matcher(strEle);
while (mEle.find()) {
String result = mEle.group(1);
System.out.println("\t\tElement: " + result);
}
}
}
}
}
但当上述的程序直接运用到 www.usd-cny.com 上时, 发现最终输出的结果为空. 也就是说一点都没有得到匹配. 这是因为上述的匹配规则过于特殊导致的, 下面给出更为普遍的匹配规则, 能够匹配如下面的格式:
格式:
<TR bgcolor=""></TR>
<TD WIDTH=""></TD>
<TD> <DIV ALIGN="center"><b><font color"">element</font></b></td> 匹配规则:
final static String REGEX_TABLE = "<table.*?>\\s*?((<tr.*?>.*?</tr>)+?)\\s*?</table>";
final static String REGEX_ROW = "<tr.*?>\\s*?(.*?)\\s*?</tr>";
final static String REGEX_ELE = "(?:<th.*?>|<td.*?>)(?:\\s*<.*?>)*(?: )?(.*?)(?: )?(?:\\s*<.*?>)*?\\s*(?:</th>|</td>)";
3.2 重新整理HtmlTable类
package com.cnblogs.grassandmoon; import java.util.regex.*;
import java.io.*; public class HtmlTable {
final static String ELEMENT_SEPARATOR = "\001";
final static String ROW_SEPARATOR = "\002"; final static String REGEX_TABLE = "<table.*?>\\s*?((<tr.*?>.*?</tr>)+?)\\s*?</table>";
final static String REGEX_ROW = "<tr.*?>\\s*?(.*?)\\s*?</tr>";
final static String REGEX_ELE = "(?:<th.*?>|<td.*?>)(?:\\s*<.*?>)*(?: )?(.*?)(?: )?(?:\\s*<.*?>)*?\\s*(?:</th>|</td>)"; public static String extract(int nStartLine, int nEndLine, BufferedReader br)
throws IOException {
String line;
String target = "";
String elements = "";
int i = 0;
// iStartLine[0] = 78;
// iEndLine[0] = 303; while ((line = br.readLine()) != null) {
++i;
if (i < nStartLine) continue;
line.trim();
target = target + line;
if (i >= nEndLine) break;
} // 正则表达式
Pattern r = Pattern.compile(REGEX_TABLE, Pattern.CASE_INSENSITIVE); // 表单的匹配
Matcher mTable = r.matcher(target); if (mTable.find()) {
String strRows = mTable.group(1).trim(); // 表单中每一行得匹配
Matcher mRow = Pattern.compile(REGEX_ROW, Pattern.CASE_INSENSITIVE).matcher(strRows);
while (mRow.find()) {
boolean firstEle = true;
String strEle = mRow.group(1).trim();
// System.out.println("\nTh or td: " + strEle); // 每一行中每个元素得匹配
Matcher mEle = Pattern.compile(REGEX_ELE, Pattern.CASE_INSENSITIVE).matcher(strEle); if (!elements.equals(""))
elements = elements + ROW_SEPARATOR;
while (mEle.find()) {
String result = mEle.group(1).trim();
if (firstEle)
elements = elements + result;
else
elements = elements + ELEMENT_SEPARATOR + result;
firstEle = false;
// System.out.println("\nElement: " + result);
}
if (!elements.equals("")) {
int len = elements.length();
elements = elements.substring(0, len-2);
}
}
} return new String(elements);
}
}
4 总结
然后再次对实现代码进行了整理, 完整的代码见:RateExchange @ git
再后续的文中, 将介绍如何使用jsoup从网页中提取相应的信息.
Date: 2014-05-12 Mon
Author: Zhong Xiewei
Org version 7.8.11 with Emacs version 24
[java] 汇率换算器实现(3)的更多相关文章
- [java] 汇率换算器实现-插曲1-正则表达式(1)
[java] 汇率换算器实现-插曲1-正则表达式(1) // */ // ]]> // */ // ]]> [java] 汇率换算器实现-插曲1-正则表达式(1) Table of C ...
- [java] 汇率换算器实现(2)
[java] 汇率换算器实现(2) // */ // ]]> // */ // ]]> [java] 汇率换算器实现(2) Table of Contents 1 系列文章地址 2 前 ...
- [java] 汇率换算器实现(1)
[java] 汇率换算器实现(1) // */ // ]]> [java] 汇率换算器实现(1) Table of Contents 1 问题描述 2 类设计 3 初步实现 3.1 建立项目 ...
- [java] 更好的书写equals方法-汇率换算器的实现(4)
[java] 更好的书写equals方法-汇率换算器的实现(4) // */ // ]]> [java] 更好的书写equals方法-汇率换算器的实现(4) Table of Content ...
- [java] 注释以及javadoc使用简介-汇率换算器的实现-插曲3
[java] 注释以及javadoc使用简介-汇率换算器的实现-插曲3 // */ // ]]> [java] 注释以及javadoc使用简介-汇率换算器的实现-插曲3 Table of C ...
- [java] jsoup使用简介-汇率换算器实现-插曲2
[java] jsoup使用简介-汇率换算器实现-插曲2 // */ // ]]> [java] jsoup使用简介-汇率换算器实现-插曲2 Table of Contents 1 系列文章 ...
- 【菜鸟学Python】案例一:汇率换算
汇率换算V1.0 案例描述: 设计一个汇率换算器程序,其功能是将外币换算成人民币,或者相反 案例分析: 分析问题:分析问题的计算部分: 确定问题:将问题划分为输入.处理及输出部分: 设计算法:计算部分 ...
- 汇率换算自然语言理解功能JAVA DEMO
>>>>>>>>>>>>>>>>>>>>>>>> 欢迎转 ...
- 万航单位换算器 V1.0 绿色版
软件名称: 万航单位换算器软件语言: 简体中文授权方式: 免费软件运行环境: Win 32位/64位软件大小: 347KB图片预览: 软件简介:万航单位换算器是一个可以随意转换单位的绿色软件,这个软件 ...
随机推荐
- 练习1-16:修改打印最长文本行的程序的主程序main,使之可以打印任意长度的输入行的长度,并尽可能多地打印文本(C程序设计语言 第2版)
该书英文配套答案 Answer to Exercise -, page Revise the main routine of the longest-line program so it will c ...
- UNITY 状态机 + SVN + 码云 下篇
上篇说到自己写的一个FSM状态机,这篇写怎么把代码和码云联系在一起! 首先,我们应该知道为什么使用码云? 码云是开源中国社区2013年推出的基于 Git 的完全免费的代码托管服务,这个服务是基于 Gi ...
- 实现Ogre的脚本分离 - 天龙八部的源码分析(一)
目的 在研究天龙八部游戏的源码之时, 发现 Ogre 材质的模板部分被单独放在一个 material 文件之内, 继承模板的其他材质则位于另外的文件, 当我使用Ogre 官方源码, 加载脚本时其不会查 ...
- UIAlertController 使用
iOS 8的新特性之一就是让接口更有适应性.更灵活,因此许多视图控制器的实现方式发生了巨大的变化.全新的UIPresentationController在实现视图控制器间的过渡动画效果和自适应设备尺寸 ...
- ABP入门系列(3)——领域层创建实体
这一节我们主要和领域层打交道.首先我们要对ABP的体系结构以及从模板创建的解决方案进行一一对应.网上有代码生成器去简化我们这一步的任务,但是不建议初学者去使用. 一.首先来看看ABP体系结构 领域层就 ...
- dojo/dom-form
表单的处理在前端开发中一样意义非凡,dojo/dom-form模块提供了一系列方法来处理表单元素.比如: fieldToObject: 将一个表单字段转化成JavaScript原生类型,可能是stri ...
- C#抓取网页HTML内容
网上很多内容采集工具,今天就自己试着写一个,发现C#可以轻松的抓去网页的内容,进而通过正则来分离出自己感兴趣的数据.下面是抓去网页内容的代码: using System; using System.C ...
- Open Source Cassandra Gitbook for Developer
Just released an open source Cassandra Gitbook for developer. http://teddymaef.github.io/learncassan ...
- 数据库MySQL开篇
作为一名前端,后天方面的知识虽说不一定要精通后台但是对后台方面的知识有一定了解是非常必要的. 今天先说一些概念方面的,因本人才疏学浅,对于数据库这方面的自学相当于摸着石头过河,有什么写的不对的地方,希 ...
- 用PHP访问数据库
<?php //1造链接.面向对象 .方式对象方式 //把对象定个名字$db //MySQLi:数据扩展类.在MySQLi里做对象() //host:代表服务器地址也叫做本机[本机服务器loca ...