- 场景
有这么个场景,我们需要某个时间点某个应用程序自动遍历和提取一堆文件中的一小部分规则的字符串
- 实现
这块baidu了下有很多种解决办法,其实最本质的问题就是查一段字符串在大的字符串(文件流)中是否存在的问题。
简单实现原理:
这块我们选择使用正则来处理, 其实这块稍稍麻烦一点的就是正则的编写了,其它代码和平常都一样
表达式 匹配内容 @author\s+((\w+\.?)+\w+)\r?\n?
@author abc.abc.com
(\w+.*\\)+(.*\.{1}\w+)$
提取文件名称时会用到
C:\abc\abc.abc
匹配路径分割符
/** * 负责实现基于正则的文件内容查找 * <ol> * <li>利用NIO机制处理文件流的读取工作</li> * <li>利用Java正则支持处理匹配</li> * </ol> * @author WangYanCheng * @version 2011-11-1 */ public class FileGrep { /** 文件字符编码 */ private CharsetDecoder decoder; /** 文件行 */ private static Pattern pattern = Pattern.compile(".*\r?\n"); /** * Constructor * @param decoder CharsetDecoder */ public FileGrep(CharsetDecoder decoder) { this.decoder = decoder; } /** * 取实例 * @param charsetInst 字符集对象 * @return fileGrepInst */ public static FileGrep getInst(Charset charsetInst) { return new FileGrep(charsetInst.newDecoder()); } /** * 文件内容匹配入口 * @param pattern 匹配串 * @param fileInst 文件对象 * @return rtnStrArr/null 文件内容匹配结果 * @throws IOException 异常信息 */ public String[] findResult4Regexp(final String pattern, File fileInst, final int groupIndex) throws IOException { final Pattern tmpPattern = Pattern.compile(pattern); final List<String> tmpArr = new ArrayList<String>(); readFile(fileInst, new InnerCallback() { public void callBack(CharBuffer charBuff) { Matcher matcherInst = FileGrep.pattern.matcher(charBuff); while (matcherInst.find()) { String tmpStrArr = matchesResult4Single(matcherInst.group(), tmpPattern, groupIndex); if (null != tmpStrArr) { tmpArr.add(tmpStrArr); } } } }); if (tmpArr.size() == 0) { return null; } String[] tmpStrArr = new String[tmpArr.size()]; return tmpArr.toArray(tmpStrArr); } /** * 内容匹配返回第一次匹配结果 * @param charBuff 字符序列 * @param pattern 匹配模式 * @param groupIndex 在匹配成功时返回的正则模式匹配分组标记 * @return rtnArr/null */ private String matchesResult4Single(CharSequence charBuff, Pattern pattern, int groupIndex) { Matcher matcherInst = pattern.matcher(charBuff); if (matcherInst.find()) { return matcherInst.group(groupIndex); } return null; } /** * 读文件内容 * @param fileInst * @throws IOException */ private void readFile(File fileInst, InnerCallback innerCallback) throws IOException { FileInputStream fins = new FileInputStream(fileInst); FileChannel fileChannel = fins.getChannel(); MappedByteBuffer mbbInst = fileChannel.map(MapMode.READ_ONLY, 0, fileChannel.size()); innerCallback.callBack(decoder.decode(mbbInst)); fileChannel.close(); } /** * 定义回调规则 * @author WangYanCheng * @version 2011-11-1 */ interface InnerCallback { /** * 回调方法 * @param charBuff 字符序列对象 */ void callBack(CharBuffer charBuff); } }
测试
/** * 测试用例 * @author WangYanCheng * @author www.www.www.baba * @version 2011-11-1 */ public class FileGrepTest { private FileGrep fileGrep; @Before public void setUp() throws Exception { fileGrep = FileGrep.getInst(Charset.forName("UTF-8")); } @After public void tearDown() throws Exception { fileGrep = null; } @Test public void testGetInst() { fail("Not yet implemented"); } @Test public void testDoWork() { String pattern = "@author\\s+((\\w+\\.?)+\\w+)\\r?\\n?"; File fileInst = FileUtils.lookup(this.getClass(), "FileGrepTest.java"); try { fileGrep.findResult4Regexp(pattern, fileInst, 1); } catch (IOException e) { e.printStackTrace(); } } }
其实如果在Linux下这事情就简单些了直接就可以使用Grep命令就可以了。
文件内容匹配
最新推荐文章于 2023-12-19 18:30:00 发布