20161207 结对编程-马尔可夫链-自动生成短文

20161207 结对编程-马尔可夫链-自动生成短文

结对伙伴:石亚鑫 20162303

需求分析

1.通过“学习”一篇文章后,随机输出新的文章。
参考资源:《瓦尔登湖》
2.仅考虑英文输入输出
3.从文件读入待”学习“文章
4.能处理标点符号(参考材料中有说明)
5.能控制输出文章的篇幅
6.通过参数指定输出的单词数
7.误差控制

  • 生成的语句要能完整结束(比如遇到句号、问号、感叹号等结束标志)。
  • 为了能实现上述条件,允许输出的单词数量误差 ±50。
  • 避免环

实现过程中的关键代码解释

    static final int NPREF = 2; //前缀个数

        static final String NOWORD = "\n"; //英语单词不再重复

        Map<Prefix,List<String>> stateTable = new HashMap<Prefix,List<String>>();

        Prefix prefix = new Prefix (NPREF,NOWORD);//刚开始的前缀

        Random random = new Random();


        public void build(InputStream in) throws Exception {
            Scanner scanner = new Scanner(in);

            while(scanner.hasNext()){
                add(scanner.next());
            }
            add(NOWORD);
        }

        private void add(String word) {
            List<String> suf = stateTable.get(prefix);
            if(suf == null){
                suf = new ArrayList<String>();
                stateTable.put(new Prefix(prefix),suf);
           }
            suf.add(word);
            prefix.pref.remove(0);
            prefix.pref.add(word);
        }


        public void generate(int nwords) throws IOException {
            FileWriter fw = new FileWriter("/Users/zhangyunqi/Desktop/qq.txt");//生成的文章储存在qq.txt中
            prefix = new Prefix(NPREF,NOWORD);
            for(int i=0; i<nwords; i++){
                List<String> suf = stateTable.get(prefix);
                int r = Math.abs(random.nextInt() % suf.size());
                String word = suf.get(r);
                if(word.equals(NOWORD)){
                    break;
                }
                System.out.print(word+" ");
                if (word.equals(".")){
                    fw.write("\n");
                }
                else
                    fw.write(word+" ");


                prefix.pref.remove(0);
                prefix.pref.add(word);
            }
            fw.close();

运行过程截图

代码托管地址

遇到的困难及解决方法

刚刚开始并没有头绪,于是上网百度,发现怎么生成前后缀关系的代码。
把输入想像成由一些互相重叠的短语构成的序列,该算法把每个短语分成两部分:一部分由多个词构成的前缀,另一部分是只包含一个词的后缀。马尔可夫链算法能够生成输出短语的序列,其方法是依据(在我们的情况下)原文本的统计性质,随机性地选择跟在前缀后面的特定后缀。采用三个词的短语就能够工作得很好——利用连续两个词构成的前缀来选择作为后缀的一个词:
设置w1和w2为文本的前两个词
输出w1和w2
循环:

  • 随机地选出w3,它是文本中w1w2的后缀中的一个
  • 打印w3
  • 把w1和w2分别换成w2和w3
  • 重复循环

选择二词前缀,则每个输出词w3都是根据它前面的一对词(w1,w2)得到的。前缀中词的个数对设计本身并没有影响,程序应该能对付任意的前缀长度。我们把一个前缀和它所有可能后缀的集合放在一起,称其为一个状态。

对结对的小伙伴做出评价

我的结对伙伴是我的室友,所以本次编程是我们坐在一起完成的。

如有参考或引用的设计、实现,请进行说明

参考:http://www.cnblogs.com/vertextao/p/6881960.html

PSP

PSP2.1 Personal Software Process Stages 预估耗时(分钟) 实际耗时(分钟)
Planning 计划 30 30
· Estimate · 估计这个任务需要多少时间 610 920
Development 开发 50 40
· Analysis · 需求分析 (包括学习新技术) 30 20
· Design Spec · 生成设计文档 30 50
· Design Review · 设计复审 (和同事审核设计文档) 60 100
· Coding Standard · 代码规范 (为目前的开发制定合适的规范) 10 10
· Design · 具体设计 100 90
· Coding · 具体编码 100 300
· Code Review · 代码复审 30 60
· Test · 测试(自我测试,修改代码,提交修改) 30 90
Reporting 报告 60 60
· Test Report · 测试报告 30 30
· Size Measurement · 计算工作量 20 20
· Postmortem & Process Improvement Plan · 事后总结, 并提出过程改进计划 30 20
合计 610 920
posted @ 2017-06-25 15:20  张韵琪  阅读(209)  评论(0编辑  收藏  举报