Java实现成语接龙
近来,想做一些算法练习,无意中想到了我们非常熟悉的成语接龙游戏(本次以四字成语为例),就想着如何用java实现成龙接龙的关键逻辑。说干就干,于是很快梳理了一下思路:
1、首先在数据库构建一个表,导入大量的成语,作为成语储备。(这是基础)
2、思考接龙逻辑,实现成语接龙。(这是核心)
首先,我们来构建成语库,根据成语接龙的游戏规则,思考了下,表至少需要以下字段:成语内容、成语首字、成语末尾字。如果成语接龙的规则再放宽,比如接龙的时候只考虑读音一致也行,那么再补充成语首字拼音、成语末尾字拼音两个字段。于是,表结构基本确定下来了,以Spring Data JPA为例,成语的Entity如下:
@Entity
@Table(name = "t_idiom")
public class IdiomEntity {@Idprivate String id = Util.getUUIDStr();private String value;//四字成语,如:龙飞凤舞private String wordS;//成语的首字private String wordE;//成语的末尾字private String pinyinS;//成语的首字拼音private String pinyinE;//成语的末尾字拼音private String paraphrase;//成语解释//为节约篇幅,此处省略get、set方法。
}
表建好之后就需要导入数据了,我从网上找了个txt版的成语大全,非常全,大概接近三万条成语。这么多数据,当然需要通过程序导入表里了,可以通过java读取txt文件的内容,加以逻辑,将数据存到表里。java读取txt文件的代码可自行研究学习,不在详细解释,因为这不是本文的重点。txt文件内容的格式如下:
读取txt文件并保存数据代码如下:
@Overridepublic void readTxt(String filePath) {File file = new File(filePath);StringBuilder result = new StringBuilder();try{BufferedReader br = new BufferedReader(new FileReader(file));//构造一个BufferedReader类来读取文件String s = null;while((s = br.readLine())!=null){//使用readLine方法,一次读一行if (s.indexOf("拼音") > 0) {String value = s.substring(0, s.indexOf("拼音")).trim();if (value.length() == 4) {IdiomEntity idiomEntityOld = idiomRepo.findFirstByValue(value);if (idiomEntityOld == null) {try {String pinyin = s.substring(s.indexOf("拼音:") + 3, s.indexOf("释义"));String paraphrase = s.substring(s.indexOf("释义:") + 3);String wordS = value.substring(0,1);String wordE = value.substring(3,4);String pinyinS = pinyin.substring(0, pinyin.indexOf(" "));String pinyinE = pinyin.substring(pinyin.lastIndexOf(" ") + 1);IdiomEntity idiomEntity = new IdiomEntity();idiomEntity.setValue(value);idiomEntity.setWordS(wordS);idiomEntity.setPinyinS(pinyinS);idiomEntity.setWordE(wordE);idiomEntity.setPinyinE(pinyinE);idiomEntity.setParaphrase(paraphrase);idiomRepo.save(idiomEntity);} catch (Throwable e) {continue;}}}}}br.close();}catch(Exception e){e.printStackTrace();}}
成语大全里已经给出了成语的汉语拼音了,非常方便,但是如果没有带拼音的话,我们也可以通过java代码获取汉字的汉语拼音,代码如下:
/*** 汉字转为拼音* @param chinese* @return*/public static String ToPinyin(String chinese){String pinyinStr = "";char[] newChar = chinese.toCharArray();HanyuPinyinOutputFormat defaultFormat = new HanyuPinyinOutputFormat();defaultFormat.setCaseType(HanyuPinyinCaseType.LOWERCASE);defaultFormat.setToneType(HanyuPinyinToneType.WITHOUT_TONE);for (int i = 0; i < newChar.length; i++) {if (newChar[i] > 128) {try {pinyinStr += PinyinHelper.toHanyuPinyinStringArray(newChar[i], defaultFormat)[0];} catch (BadHanyuPinyinOutputFormatCombination e) {e.printStackTrace();}}else{pinyinStr += newChar[i];}}return pinyinStr;}
读入成语数据,算是完成了第一步,如图:
一共28603条成语,成语库很丰富了。
接下来,最关键的一步,实现成语接龙的逻辑,就以最常见的游戏规则(接龙的时候前后两个成语的首尾字必须一致)为例。思路如下:根据输入的第一个成语(也就是龙头句),根据它的末尾字(也就是关节字)来接龙,我们可以去数据库里检索第二个成语(首字等于龙头句的末尾字)。检索到的第二个成语肯定不止一个,按照同样逻辑,检索下一个成语,每次检索都会有多个答案。就像一棵树一样,龙头句相当于树的根部,每次接龙多会分N个树杈,直到无法接上(到达叶子)。也就是说每条从树根到达某个叶子节点的路径都是成语接龙的答案。如何得到这些答案,并输出出来,核心就是利用递归和遍历。实现代码如下:
@Overridepublic void idiomPlay(String sIdiom) { //sIdiom:输入的成语(龙头句)String wordE = sIdiom.substring(3, 4); //关节字doPlay(sIdiom, wordE);}//递归方法public void doPlay(String idiomStr, String wordE){List<IdiomEntity> idiomEntities = idiomRepo.findAllByWordS(wordE); //根据关节字检索下一条成语if (idiomEntities.size() > 0) {for (IdiomEntity entity : idiomEntities) {if (idiomStr.indexOf(entity.getValue()) > -1) { //如果检索到的成语已经在之前的成语串里,则停止递归System.out.println(idiomStr);} else {doPlay(idiomStr + "->" + entity.getValue(), entity.getWordE());}}} else { //检索不到下一条成语,该路径完成System.out.println(idiomStr);}}
输入“龙飞凤舞”,执行结果片段如下:
由于成语库非常大,接龙的答案会非常多,一时半会是执行不完的。在测试的过程中,发现有时会输出重复的答案,分析发现,在成语串已经非常长的情况下,检索下一条成语的时候如果检索到很多个,则可能会出现其中多个是已经在之前成语串中出现过,根据程序逻辑,这种情况会输出几条重复的答案,但是不会出现死循环。可以利用set集合去重,本文不再详述。
这样,一个简单的成语接龙就实现了,其他接龙玩法可依本例扩展,不再详述。
Java实现成语接龙相关推荐
- Java 算法 单词接龙
目录标题 题目描述 解题思路 代码 题目描述 单词接龙是一个与我们经常玩的成语接龙相类似的游戏,现在我们已知一组单词,且给定一个开头的字母,要求出以这个字母开头的最长的"龙"(每个 ...
- javaweb成语接龙
idiom.jsp <%@ page contentType="text/html;charset=UTF-8" language="java" %> ...
- 成语接龙(英语单词链)
<构建之法>练习题 大家经常玩成语接龙游戏,我们试一试英语的接龙吧:一个文本文件中有N 个不同的英语单词, 我们能否写一个程序,快速找出最长的能首尾相连的英语单词链,每个单词最多只能用一次 ...
- Javaweb 成语接龙(实验)
这篇文章介绍一下如何实现成语接龙.严格意义上来说我实现的是四个字的词语接龙.没有引入成语库,只判断是否为四个字以及前一个词最后一个字和后一个词第一个字是否相同.用两个jsp页面就可以实现,非常简单基础 ...
- QQ成语接龙,红包辅助-(附源码+demo)
前几天QQ出了个成语接龙红包,基本上搜索成语都是件难事,我最近刚好开发了一款影视app,发现这个成语接龙,并不是特别难,就花半天顺便写了一下, 先看一下图片 大概的思路,就是一个php搜索接口,调用m ...
- 微信公众平台开发—成语接龙
因为申请的是个人未认证的订阅号,开启开发者模式以后没有菜单,只能使用接收消息-回复消息的方式来开发 一.实现思路 1.成语接龙题库 成语接龙的题库比24点的复杂一些,数量也很大,我建的表字段是:&qu ...
- 成语接龙(字符串,思路,按长度排序)
成语接龙 Time Limit: 3000/1000 MS (Java/Others) Memory Limit: 65536/65536 K (Java/Others) Total Submi ...
- 中国电子学会图形化四级编程题:成语接龙
「青少年编程竞赛交流群」已成立(适合6至18周岁的青少年),公众号后台回复[Scratch]或[Python],即可进入.如果加入了之前的社群不需要重复加入. 我们将有关编程题目的教学视频已经发布到抖 ...
- 8个成语接龙首尾相连_七七八八成语接龙_八开头的成语大全,八结尾的成语接龙...
向您解答有哪些七七八八的成语接龙是什么?用最后八字结尾来接八开头的成语,就是七七八八的成语接龙了.另外,我们也要知道七七八八的造句子内容更新请继续访问www.mygx.net.,无 第一位 第二位 第 ...
- python——成语接龙小游戏
小试牛刀的简易成语接龙. 思路-- 1.网上下载成语字典的txt版本 2.通过python进行处理得到格式化的成语,并整理成字典(python字典查找速度快) 3.python程序,查找 用户输入的最 ...
最新文章
- Swift语言中class、struct、enum的联系与区别
- 用c语言大一个三角形图形,c语言图形,请高手修改,效果是一个三角形绕一点旋转一周...
- 【Mac软件推荐】Alfred:Mac下最好的快速启动工具
- Express engine 学习笔记 - 工作在反向代理背后的 Express 设置
- (Z)使用SignalTAP II为了避免某些节点被弄丢, 必须要关闭的编译选项
- csv中包含多余换行符_Python3爬虫之猫眼电影TOP100(requests、lxml、Xpath、CSV)
- java uuid fasterxml_可笑!可悲!可叹!你竟然还不知道Java如何生成UUID?
- 工具使用教程(二)【Github上传文件大于100M的文件】
- 使用VUE分分钟写一个验证码输入组件
- 编写一个程序,新建一个文件:d:\abc.txt,从键盘输入abc.txt内容(不超过100个字符)。然后新建另外一个文件:d:\def.txt,将abc.txt的前10个字符复制到def.txt上
- 平面变压器的设计(翻译)(4)
- 大数据处理应遵循的四大原则
- android手机图标 足球球星,C罗梅西最抢眼 足球巨星们都用什么手机
- 小学期云效能训练营-Day04
- 读书,意味着你还不服输
- hive 中创建表的三种方式
- CDC *pDC=GetDC();具体是什么意思?
- 机器人开发--设计范式
- JS跨域设置和取Cookie(二)
- [VOT15](2021CVPR)Alpha-Refine: Boosting Tracking Performance by Precise Bounding Box Estimation