于是写了一个小程序,可以自动扫描电影在豆瓣的评分,并排序。
程序说明:
1 使用了反射和自定义classloader调用main方法,使得命令行不用指定jar包。
java -cp .;allen_base-1.0.jar allen.program.Driver allen.douban.main.LocalFilmRating
try { Class<?> type = myClassLoader.loadClass(mainClass); Method method = type.getMethod("main", String[].class); method.invoke(null, (Object) args0); } catch (Exception e) { throw new RuntimeException(e); }
2 使用了org.json包调用豆瓣API。
3 使用了多线程控制调用豆瓣API的频率。
private static int limitInMinutes = Config.LimitInMinutes; private static AtomicInteger invokeCounter = new AtomicInteger( limitInMinutes); private static Thread monitorThread = new Thread() { @Override public void run() { while (true) { try { Thread.sleep(60000); } catch (InterruptedException e) { System.out .println(e); } invokeCounter .set(limitInMinutes); } } };
private static void checkCounter() { int counter = invokeCounter.decrementAndGet(); if (counter >= 0) { log.debug("pass counter = " + counter); return; } else { log.debug("deny counter = " + counter); } try { Thread.sleep(1000); } catch (InterruptedException e) { log.err(e); } checkCounter(); }
4 使用了配置文件控制程序的运行。
#本地电影缓存目录。 MovieCacheDir=I:\douban_base\movie\ #本地个人缓存目录。 CelebrityCacheDir=I:\douban_base\celebrity\ #LocalFilmDirs=K:\todo,K:\allen_film #本地电影目录。可以多个目录以逗号分隔。 LocalFilmDirs=K:\download #豆瓣API的调用次数限制,每分钟。豆瓣API上面说不能超过40/min,实际上可以。 LimitInMinutes=40 #本地电影名称中需要过滤掉的字符串。 WordIgnoreInFilmTitle=BD,1280,高清,中字,CD,迅雷,下载,DVD,中英字幕,中英双字,720p #可以处理的视频后缀名称。字母小写。 SuffixOfFiles=wmv,asf,asx,rm,rmvb,mpg,mpeg,mpe,dat,vob,dv,3gp,3g2,mov,avi,mkv,mp4,m4v,flv,xv #不可以处理的文件后缀名称。字母小写。 IgnoreSuffixOfFiles=srt,torrent,idx,sub,rar,txt,jpg,zip,mp3
其中
WordIgnoreInFilmTitle配置了电影名称中被替换为空字符串的关键字。
SuffixOfFiles配置了可以处理的视频格式。
IgnoreSuffixOfFiles配置了不可以处理的文件格式。
5 为了减少对豆瓣API的调用次数,对于相似的电影名称进行了处理。
/** * 处理相似的名字。2个名字有一个字符不同,其他相同,则认为2个名字相似。 * */ public static List<String> filterSimilarName(List<String> filmNames) { if (filmNames.size() <= 1) { return filmNames; } List<String> result = new ArrayList<String>(); result.add(filmNames.get(0)); //相同字符的index。 int lastSimilarIndex = -1; for (int i = 1; i < filmNames.size(); i++) { String toHandleName = filmNames.get(i); String lastHandleName = result.get(result.size() - 1); int similarIndex = getSimilar(lastHandleName, toHandleName); if (similarIndex == -1) { if (lastSimilarIndex != -1) { lastHandleName = lastHandleName.substring(0, lastSimilarIndex) + lastHandleName.substring(lastSimilarIndex + 1); result.set(result.size() - 1, lastHandleName); } result.add(toHandleName); lastSimilarIndex = -1; } else { //不考虑连续相似的字符串,相似位置不同的情况。 lastSimilarIndex = similarIndex; } } return result; } private static int getSimilar(String str1, String str2) { if (StringUtil.isEmptyString(str1) || StringUtil.isEmptyString(str2)) { return -1; } if (str1.length() != str2.length()) { return -1; } int similarIndex = -1; int differenceCount = 0; for (int i = 0; i < str1.length(); i++) { char c1 = str1.charAt(i); char c2 = str2.charAt(i); if (c1 != c2) { differenceCount++; similarIndex = i; } } if (differenceCount == 1) { return similarIndex; } else { return -1; } }
6 日志可以修改log4jconfig.xml控制。
7 结果可以在biz.log中查看。
本机跑结果如下:
INFO - 94 美丽人生
INFO - 93 阿甘正传
INFO - 91 天堂电影院
INFO - 91 鬼子来了
INFO - 91 搏击俱乐部
INFO - 91 海上钢琴师
INFO - 91 两杆大烟枪
INFO - 91 黄金三镖客
INFO - 91 三傻大闹宝莱坞
INFO - 90 指环王3:王者无敌
INFO - 90 美国往事
INFO - 90 教父2
INFO - 90 少年派的奇幻漂流
INFO - 89 楚门的世界
INFO - 89 上帝之城
INFO - 89 西游记大结局之仙履奇缘
INFO - 89 活着
INFO - 89 泰坦尼克号
INFO - 89 钢琴家
INFO - 88 指环王1:魔戒再现
INFO - 88 指环王2:双塔奇兵
INFO - 88 低俗小说
INFO - 88 天使爱美丽
INFO - 88 与狼共舞
INFO - 88 西游记第一百零一回之月光宝盒
INFO - 88 地球上的星星
INFO - 88 让子弹飞
INFO - 88 精英部队2:大敌当前
INFO - 87 大鱼
INFO - 87 黑客帝国
INFO - 87 剪刀手爱德华
INFO - 87 拯救大兵瑞恩
INFO - 87 芙蓉镇
INFO - 87 狮子王
INFO - 87 致命魔术
INFO - 86 猜火车
INFO - 86 纵横四海
INFO - 86 杀人回忆
INFO - 86 绿里奇迹
INFO - 86 西伯利亚的理发师
INFO - 86 喜宴
INFO - 86 V字仇杀队
INFO - 86 谍影重重3
INFO - 86 哈利·波特与死亡圣器(下)
INFO - 86 老爷车
INFO - 86 燃情岁月
INFO - 85 非常嫌疑犯
INFO - 85 洛城机密
INFO - 85 西西里的美丽传说
INFO - 85 费城故事
INFO - 85 末代皇帝
INFO - 85 美国X档案
INFO - 85 全金属外壳
INFO - 85 偷拐抢骗
INFO - 85 人工智能
INFO - 85 记忆碎片
INFO - 85 盲井
INFO - 85 赛德克·巴莱
INFO - 84 终结者2
INFO - 84 英国病人
INFO - 84 勇闯夺命岛
INFO - 84 加勒比海盗
INFO - 84 时时刻刻
INFO - 84 两小无猜
INFO - 84 黑天鹅
INFO - 84 朗读者
INFO - 84 这个男人来自地球
INFO - 84 蝙蝠侠:黑暗骑士崛起
INFO - 84 11度青春之《老男孩》
INFO - 83 歌剧魅影
INFO - 83 黑鹰坠落
INFO - 83 爱情是狗娘
INFO - 83 现代启示录
INFO - 83 不可饶恕
INFO - 83 荒岛余生
INFO - 83 谍影重重2
INFO - 83 了不起的狐狸爸爸
INFO - 83 凯尔经的秘密
INFO - 83 谜一样的双眼
INFO - 82 角斗士
INFO - 82 星球大战
INFO - 82 一级恐惧
INFO - 82 星球大战2:帝国反击战
INFO - 82 落水狗
INFO - 82 秋天的童话
INFO - 82 黑客帝国3:矩阵革命
INFO - 82 傲慢与偏见
INFO - 82 米尔克
INFO - 82 国王的演讲
INFO - 81 巴菲的奇妙命运
INFO - 81 夺宝奇兵3
INFO - 81 星球大战3:绝地归来
INFO - 81 罗塞塔
INFO - 81 喜剧之王
INFO - 81 黑客帝国2:重装上阵
INFO - 81 黑皮书
INFO - 81 霍比特人1:意外之旅
INFO - 81 碟中谍4
INFO - 81 社交网络
INFO - 81 黄海
INFO - 80 钢琴课
INFO - 80 英雄本色2
INFO - 80 小鬼当街
INFO - 80 卡特教练
INFO - 80 复仇者联盟
INFO - 80 葬礼上的死亡
INFO - 80 杀手没有假期
INFO - 80 X战警:第一战
INFO - 80 127小时
INFO - 79 苔丝
INFO - 79 大象
INFO - 79 精武英雄
INFO - 79 监狱风云
INFO - 79 星球大战前传1:幽灵的威胁
INFO - 79 九品芝麻官
INFO - 79 十二猴子
INFO - 79 鳗鱼
INFO - 79 你丫闭嘴!
INFO - 79 蝙蝠侠:侠影之谜
INFO - 79 星球大战前传3:西斯的复仇
INFO - 79 风吹麦浪
INFO - 79 四月三周两天
INFO - 79 白丝带
INFO - 79 猩球崛起
INFO - 79 大地惊雷
INFO - 79 单车少年
INFO - 78 迷失东京
INFO - 78 冰血暴
INFO - 78 樱桃的滋味
INFO - 78 夺宝奇兵
INFO - 78 国产凌凌漆
INFO - 78 华氏911
INFO - 78 加勒比海盗2:聚魂棺
INFO - 78 决战犹马镇
INFO - 78 老无所依
INFO - 78 立春
INFO - 78 人生不再重来
INFO - 77 云上的日子
INFO - 77 一条叫旺达的鱼
INFO - 77 碟中谍
INFO - 77 看得见风景的房间
INFO - 77 星球大战前传2:克隆人的进攻
INFO - 77 孔雀
INFO - 77 加勒比海盗3:世界的尽头
INFO - 77 卡波特
INFO - 77 美国黑帮
INFO - 77 潘神的迷宫
INFO - 77 孔雀王2 幻影城
INFO - 76 食神
INFO - 76 黄飞鸿之二:男儿当自强
INFO - 76 秋菊打官司
INFO - 76 毁灭之路
INFO - 76 黑社会
INFO - 76 功夫2
INFO - 76 理发师陶德
INFO - 76 看车人的七月
INFO - 76 预言者
INFO - 76 斗牛
INFO - 76 七个神经病
INFO - 75 性、谎言和录像带
INFO - 75 黄飞鸿之三:狮王争霸
INFO - 75 我的父亲母亲
INFO - 75 菊豆
INFO - 75 机械师
INFO - 75 虎胆龙威4