首页 AI Studio教育版 帖子详情
作业帖 | NLP+推荐-深度学习集训营
收藏
快速回复
AI Studio教育版 其他课程答疑 17676 149
作业帖 | NLP+推荐-深度学习集训营
收藏
快速回复
AI Studio教育版 其他课程答疑 17676 149

百度深度学习集训营第二阶段的NLP+推荐系统内容开讲啦,每个阶段的作业都将有各自的奖励,欢迎大家学习~

PS:如遇帖子过期、审核不通过的情况,请先复制内容保存在word文档,然后根据提示,完成个人实名验证,刷新后重新粘贴复制的内容,即可提交~

欢迎大家报名参加~

请大家按照作业格式将作业回帖在下面,并备注自己的AI Studio用户名~

 

2月27日第二次作业

作业奖励:3月2日中午12点之前完成,会从中挑选10位回答优秀的同学获得飞桨定制数据线+本

实践作业:(必做)

路径:AI Studio课程-作业-NLP作业2

•请尝试用飞桨实现一个CBOW模型,并使用text8语料进行训练(或尝试提高skip-gram的训练速度)

附加题:(选做,答案回复在作业帖下)

•打开你的脑洞,尝试embedding的各种花样玩法,比如计算同义词,进行推理,将embedding进行聚类,或者用t-sne进行可视化。

附加题回复格式:

AI Studio用户名:XXXX

作业2-1附加题:XXX

 

2月25日第一次作业

作业奖励: 3月2日中午12点之前完成,会从中挑选10位幸运的同学获得飞桨定制数据线+本

作业1-1

(1)下载飞桨本地并安装成功,将截图发给班主任
(2)学习使用PaddleNLP下面的LAC模型或Jieba分词
LAC模型地址:https://github.com/PaddlePaddle/models/tree/release/1.6/PaddleNLP/lexical_analysis
Jieba模型:https://github.com/fxsjy/jieba
(3)对人民日报语料完成切词,并通过统计每个词出现的概率,计算信息熵
语料地址:https://github.com/fangj/rmrb/tree/master/example/1946%E5%B9%B405%E6%9C%88

作业1-2

(1)思考一下,假设输入一个词表里面含有N个词,输入一个长度为M的句子,那么最大前向匹配的计算复杂度是多少?
(2)给定一个句子,如何计算里面有多少种分词候选,你能给出代码实现吗?
(3)除了最大前向匹配和N-gram算法,你还知道其他分词算法吗,请给出一段小描述。

回复作业格式:

AI Studio用户名:XXXX

作业1-1:XXX

作业1-2:

(1)XXX

(2)XXX

 

报名流程:

1.加入QQ群:677320960,班主任会在QQ群里进行学习资料、答疑、奖品等活动

2.点此链接,加入课程报名并实践:https://aistudio.baidu.com/aistudio/course/introduce/888

温馨提示:课程的录播会在3个工作日内上传到AI studio《百度架构师手把手教深度学习》课程上

8
收藏
回复
全部评论(149)
时间顺序
Hazelnut
#62 回复于2020-02

AI Studio用户名:Hazelnut

作业1-1:

下载飞桨本地并安装成功

对人民日报语料完成切词,并通过统计每个词出现的概率,计算信息熵
代码:

import os 
import jieba
from math import log

jieba.enable_paddle()# 启动paddle模式。 0.40版之后开始支持,早期版本不支持

filename = []                   # 文件名
dir_path = './1946年05月/'    # 语料文件夹
symbol = ['“', '”', '!', ',', '。', '?', '(', ')', '#', ':', '、', '(', ')','【' ,'】', '(', ')', '-']
sentence = []       # 语料中的句子
words = []          # 分词结果
d = {}              # 各单词出现次数

# 读取文件名
for root, dirs, files in os.walk(dir_path):
    filename.append(files)
filename = filename[0]


# 读取文件内容
count = 0
for file in filename:
    with open(dir_path + file, 'r',encoding='utf-8') as f:
        string = f.read()
        for s in symbol:
            string = string.replace(s, '')  # 去除符号
        string = string.split('\n')
        sentence += string
    count += 1
    if count % 50 == 0:
        print('已读取', str(count), '个文件')

# 分词
for string in sentence:
    seg_list = jieba.cut(string, use_paddle=True) # 使用paddle模式
    for seg in list(seg_list):
        words.append(seg)

# 统计每个单词出现次数
for word in words:
    if word in d:
        d[word] += 1
    else:
        d[word] = 1

# 输出结果
with open('seg_count.txt', 'w', encoding = 'utf-8') as f:
    for key, value in d.items():
        f.write(key + ' ' + str(value) + '\n')

    
# 计算信息熵
entropy = 0.0
words_count = len(words)
for key, value in d.items():
    t = value / words_count
    entropy +=  t * log(t, 2)
entropy = -entropy
print(entropy)

 

运行结果

各个词出现次数存储在文件 seg_count.txt 中,部分结果如下:

 

作业1-2
思考一下,假设输入一个词表里面含有N个词,输入一个长度为M的句子,那么最大前向匹配的计算复杂度是多少?
最坏情况下,即每个字对应一个词,单词最大长度为M,则每次取词需要配对M×N次 ,一共需要配对M次,复杂度为O(MMN)

给定一个句子,如何计算里面有多少种分词候选,你能给出代码实现吗?
代码如下:

def ways(length):
    if length == 0:
        return 0
    elif length == 1:
        return 1
    elif length == 2:
        return 2 
    else:
        result = 0
        for i in range(0, length):
            result += ways(length - i)
        return result

 

除了最大前向匹配和N-gram算法,你还知道其他分词算法吗,请给出一段小描述。
后向最大匹配算法
与前向最大匹配算法类似,但是方向相反,从后向前寻找词典中存在的词并输出。
例如最大单词长度为3,对句子:“百度飞桨好”
第一轮:
取子串 “飞桨好”,扫描词典中单词,没有匹配,子串长度减 1 变为“桨好”。
取子串 “桨好”,扫描词典中单词,没有匹配,子串长度减 1 变为“好”。
取子串 “好”,扫描词典中单词,匹配。
第二轮:
取子串 “度飞桨”,扫描词典中单词,没有匹配,子串长度减 1 变为“飞桨”。
取子串 “飞桨”,扫描词典中单词,匹配。
第三轮:
取子串 “百度”,扫描词典中单词,匹配。
得出结果为:百度 / 飞桨 / 好

0
回复
相依相守
#63 回复于2020-02

AI Studio用户名:相依相守

作业1-1:

(1):已截图给班主任

(2):

jieba模型学习:

LAC模型学习:


(3) 对人名日报分词

import jieba
import os 
import math
import re
from collections import Counter


word_list = []
path = os.path.abspath(os.path.join(os.getcwd(), "../../.."))+"/resources/1946y05m/"  # 由于项目结构分级,获取预料地址

for file in os.listdir(path):
    file_temp = os.path.join(path,file)  # 获取子语料文件
    content = open(file_temp, encoding="utf-8").read()
    content=re.sub('\W+','',content).replace("_",'')  # 去除符号和下划线
    seg_list = jieba.cut(content)
    word_list += seg_list

# 统计词频
word_count = Counter(word_list)
word_all_count = len(word_list)

# 计算信息熵
info_entropy = 0

for word, count in word_count.items():
    freq = count/word_all_count
    info_entropy += freq*math.log(freq, 2)
info_entropy = -info_entropy

print("信息熵:",info_entropy)

结果:

作业1-2:

(1) 答:N*(M+M-1+M-2+....+2+1)=(N+NM)/2 ,  计算复杂度为O(NM^2)

(2) 自己没有想出来结果.  看帖子回复,已经有答案了.自己跟着练习了,就不贴重复答案了

(3)

    a.逆向最大匹配法(BMM),对于输入的一个文本序列从右至左,以贪心的算法切分出当前位置上长度最大的词

    b.基于序列标注的分词算法,如基于HMM的分词方法,其属于由字构词的分词方法,由字构词的分词方法思想并不复杂,它是将分词问题转化为字的分类问题(序列标注问题)。从某些层面讲,由字构词的方法并不依赖于事先编制好的词表,但仍然需要分好词的训练预料 

0
回复
慕蟾宫
#64 回复于2020-02

AI Studio用户名:慕蟾宫

作业1-1:

(1)作业已发送班主任。其中遇到的问题是:python -m pip install paddlepaddle -i https://pypi.tuna.tsinghua.edu.cn/simple失败,如图所示

随后知道,问题在于命令提示符未获得管理员权限

解决办法:命令提示符—右键—以管理员身份运行

随后飞桨本地安装成功,如图

 

(2)jieba学习

运行结果:

(3)人民日报语料切词,通过统计每个词出现的概率,计算信息熵

计算结果:

作业1-2:

(1)Q:思考一下,假设输入一个词表里面含有N个词,输入一个长度为M的句子,那么最大前向匹配的计算复杂度是多少?

          A:最大前向匹配计算复杂度为 N*M^2

(2) Q:给定一个句子,如何计算里面有多少种分词候选,你能给出代码实现吗?    

          A:

结果:

(3) Q:除了最大前向匹配和N-gram算法,你还知道其他分词算法吗,请给出一段小描述。

          A:最大前向匹配属于基于词表的分词算法,N-gram属于基于统计模型的分析算法,此外:

          1.基于词表的分词算法

              a)逆向最大匹配法(BMM):类比前向匹配法,顺序相反

              b)双向最大匹配法:正向与逆向结合

          2.基于序列标注的分词算法

             基于HMM的分词方法:将分词问题转化为字的分类问题

 

1
回复
ExileSaber
#65 回复于2020-03

作业1-1

 

(1)

         已发给班主任

 

(2)

import jieba

import jieba.posseg as pseg

import paddlehub as hub

 

module = hub.Module(name="lac")

 

 

test_text = ["今天是个好日子", "天气预报说今天要下雨", "下一班地铁马上就要到了"]

inputs = {"text": test_text}

results = module.lexical_analysis(data=inputs)

 

for result in results:

    print('LAC分词')

    print(result)

 

 

results = []

for text in test_text:

    words = pseg.cut(text)

    d = {}

    word = []

    tag = []

    for w, t in words:

        word.append(w)

        tag.append(t)

    d['word'] = word

    d['tag'] = tag

    results.append(d)

 

for result in results:

    print('jieba分词,默认模式')

    print(result)

 

 

results = []

for text in test_text:

    # jieba.enable_paddle()  # 启动paddle模式

    words = pseg.cut(text, use_paddle=True)

    d = {}

    word = []

    tag = []

    for w, t in words:

        word.append(w)

        tag.append(t)

    d['word'] = word

    d['tag'] = tag

    results.append(d)

 

for result in results:

    print('jieba分词,启动paddle模式')

print(result)

(3)该题读取文件预处理部分有借鉴别人的做法, 之后字典的生成方法采用了get()函数简化了代码,另外还看到一个问题最后输出排行前几的词的时候有索引值问题,做了修改

作业1-2

(1)采用最大前向匹配最坏的情况意味着句子分词结果为一个字一个字,并且每个字都需要遍历词表全部,第一次为N次匹配,第二次为2N次匹配,…第k次为kN次匹配,…。所以最后的匹配结果次数为N * (M + M-1 + … + 2 + 1),得到最后的复杂度为O(N * M^2)

 

(2)

(3)查阅资料知道的一种算法

联想—回溯法

这种方法要求建立三个知识库——特征词词库、实词词库和规则库。首先将待切分的汉字字符串序列按特征词词库分割为若干子串,子串可以是词,也可以是 由几个词组合而成的词群;然后,再利用实词词库和规则库将词群再细分为词。切词时,要利用一定的语法知识,建立联想机制和回溯机制。联想机制由联想网络和 联想推理构成,联想网络描述每个虚词的构词能力,联想推理利用相应的联想网络来判定所描述的虚词究竟是单独成词还是作为其他词中的构词成分。回溯机制主要 用于处理歧义句子的切分。联想—回溯法虽然增加了算法的时间复杂度和空间复杂度,但这种方法的切词正确率较高,是一种行之有效的方法。

0
回复
晓飞好
#66 回复于2020-03

AI Studio用户名: 晓飞好

作业1-1:

(1) 截图已发送

(2)

(3)

import os
import jieba
from collections import Counter
import math
import re

def remove_punc(line):
    if(line.strip()==''):
        return ''
    rule = re.compile(u"[^a-zA-Z0-9\u4E00-\u9FA5]")
    line = rule.sub('',line)
    return line


if __name__ == '__main__':
    currPath = os.getcwd()
    fileParentPath = currPath+"/homework1/data/"
    files = os.listdir(fileParentPath)

    allNewsString = ""
    for file in files:
        fileFullPath = fileParentPath + file
        try:
            with open(fileFullPath,encoding='utf8') as f:
                str = ""
                for line in iter(f):
                    str = str + line
        except:
            with open(fileFullPath, encoding='gbk') as f:
                iter_f = iter(f)
                str = ""
                for line in iter_f:
                    str = str + line
        allNewsString = allNewsString + str
    re_allNews = remove_punc(allNewsString)
    print(allNewsString)
    stopwordList = ["的", "在", "是", "之", "与", "了"]
    # 分词
    word_cut_list = " ".join([word for word in list(jieba.cut(re_allNews)) if word not in stopwordList])
    new_word_cut_list = word_cut_list.split(" ")
    # 统计每个词的频率
    word_freq = Counter(new_word_cut_list)
    print(word_freq)
    # 计算信息熵
    all_word_num = len(new_word_cut_list)
    information_entropy = 0
    for i in word_freq:
        word_freq[i] /= all_word_num
        freq = word_freq[i]
        information_entropy += freq * math.log(freq, 2)
    information_entropy = -information_entropy
    print("计算得出的信息熵为:", information_entropy)



1-2

(1)比较次数是N*(m(m+1)/2),时间复杂度是O(N*M^2)

(2)

import jieba

test_string = "南京市长江大桥"
word_dict= list(jieba.cut(test_string,cut_all=True))
print("句子中的单词包括:",word_dict)


def count_seg_ways(candi, remained, dict):
    if len(remained) == 0:
        print("/".join(candi))
        return 1
    count = 0
    for i in range(1, len(remained)+1):
        if remained[:i] not in dict:
            continue
        count += count_seg_ways(candi+[remained[:i]], remained[i:], dict)
    return count


print("候选数", count_seg_ways([], test_string, word_dict))

(3)
基于模型的分词:HMM,朴素贝叶斯
基于判别式模型分词算法:判别式模型主要有感知机、SVM支持向量机、CRF条件随机场、最大熵模型

 

 

 

0
回复
prepared
#67 回复于2020-03

AI Studio用户名:18801936053

作业1-1

(1)下载飞桨本地并安装成功,将截图发给班主任

已经把安装图片发给班主任。

(2)学习使用PaddleNLP下面的LAC模型或Jieba分词

LAC模型地址:https://github.com/PaddlePaddle/models/tree/release/1.6/PaddleNLP/lexical_analysis

Jieba模型:https://github.com/fxsjy/jieba

学习jieba模型:

jieba 是目前最好的 Python 中文分词组件,它主要有以下 3 种特性:

支持 3 种分词模式:

  • 精确模式
  • 全模式
  • 搜索引擎模式
  • 支持繁体分词
  • 支持自定义词典

使用jieba进行分词练习:

with open(os.path.abspath(path), “r”, encoding=’utf-8’) as file:
filecontext = file.read();
print(filecontext)

分词

seg_list = jieba.cut(filecontext, cut_all=True)
print(“[精确模式]:” + “/“.join(seg_list))

(3)对人民日报语料完成切词,并通过统计每个词出现的概率TF,计算信息熵 语料地址:

https://github.com/fangj/rmrb/tree/master/example/1946%E5%B9%B405%E6%9C%88

3.1 计算每个词的TF以及信息熵

构造词典,统计每个词的频率,并计算信息熵

def calc_tf(corpus):

统计每个词出现的频率

word_freq_dict = dict()
for word in corpus:
if word not in word_freq_dict:
word_freq_dict[word] = 1
word_freq_dict[word] += 1

将这个词典中的词,按照出现次数排序,出现次数越高,排序越靠前

word_freq_dict = sorted(word_freq_dict.items(), key=lambda x:x[1], reverse=True)

计算TF概率

word_tf = dict()

信息熵

shannoEnt = 0.0

按照频率,从高到低,开始遍历,并未每个词构造一个id

for word, freq in word_freq_dict:

计算p(xi)

prob = freq / len(corpus)
word_tf[word] = prob
shannoEnt -= prob*log(prob, 2)
print(len(word_freq_dict))
return word_tf, shannoEnt

输出结果:

数据集大小,size: 163039

信息熵:14.047837802885464

作业1-2

(1)思考一下,假设输入一个词表里面含有N个词,输入一个长度为M的句子,那么最大前向匹配的计算复杂度是多少?

O(N*M^2)

for index in range(M):
for i in range(index+1):

判断词典中有没有这个词,时间复杂度是N

所以总复杂度: O(N*M^2)

(2)给定一个句子,如何计算里面有多少种分词候选,你能给出代码实现吗?

2^(n-1)

n为句子长度

def cut_num(input_str_len):
‘’’
:param input_str_len: 句子长度
:return:
‘’’

if(input_str_len == 1):
return 1
elif(input_str_len == 2):
return 2
else:
return 2 * cut_num(input_str_len-1)

print(str(cut_num(4)))

(3)除了最大前向匹配和N-gram算法,你还知道其他分词算法吗,请给出一段小描述。

  • 基于词表的分词方法
  1. 正向最大匹配法(forward maximum matching method, FMM)
  2. 逆向最大匹配法(backward maximum matching method, BMM)
  • N-最短路径方法
  1. 基于统计模型的分词方法
  2. 基于N-gram语言模型的分词方法
  • 基于序列标注的分词方法
  1. 基于HMM的分词方法
  2. 基于CRF的分词方法
  3. 基于词感知机的分词方法
  4. 基于深度学习的端到端的分词方法
0
回复
W
WangHiro
#68 回复于2020-03

1-1

(1)截图已发送给班主任

(2) 学习使用Jieba分词

(3) 对人民日报语料完成切词,并通过统计每个词出现的概率,计算信息熵

作业1-2

(1)

采用最大前向匹配最坏的情况意味着句子分词结果为一个字一个字,并且每个字都需要遍历词表全部。所以最后的匹配结果次数为N * (M + M-1 + … + 2 + 1),得到最后的复杂度为O(N * M^2)

(2)     


(3)

最大前向匹配属于基于词表的分词算法,N-gram属于基于统计模型的分析算法,此外:

1.基于词表

              a)逆向最大匹配法(BMM):类比前向匹配法,顺序相反

              b)双向最大匹配法:正向与逆向结合

2.基于统计模型

a)隐马尔可夫模型:HMM模型认为在解决序列标注问题时存在两种序列,一种是观测序列,即人们显性观察到的句子,而序列标签是隐状态序列,即观测序列为X,隐状态序列是Y,因果关系为Y->X。因此要得到标注结果Y,必须对X的概率、Y的概率、P(X|Y)进行计算,即建立P(X,Y)的概率分布模型。

b)CRF分词算法:CRF可以看作一个无向图模型,对于给定的标注序列Y和观测序列X,对条件概率P(Y|X)进行定义,而不是对联合概率建模。CRF可以说是目前最常用的分词、词性标注和实体识别算法,它对未登陆词有很好的识别能力,但开销较大

 

 

0
回复
W
WangHiro
#69 回复于2020-03

AI Studio用户名:WangHiro

作业1-1

(1)截图已发送给班主任

(2) 学习使用Jieba分词

(3) 对人民日报语料完成切词,并通过统计每个词出现的概率,计算信息熵

作业1-2

(1)

采用最大前向匹配最坏的情况意味着句子分词结果为一个字一个字,并且每个字都需要遍历词表全部。所以最后的匹配结果次数为N * (M + M-1 + … + 2 + 1),得到最后的复杂度为O(N * M^2)

(2)     


(3)

最大前向匹配属于基于词表的分词算法,N-gram属于基于统计模型的分析算法,此外:

1.基于词表

              a)逆向最大匹配法(BMM):类比前向匹配法,顺序相反

              b)双向最大匹配法:正向与逆向结合

2.基于统计模型

a)隐马尔可夫模型:HMM模型认为在解决序列标注问题时存在两种序列,一种是观测序列,即人们显性观察到的句子,而序列标签是隐状态序列,即观测序列为X,隐状态序列是Y,因果关系为Y->X。因此要得到标注结果Y,必须对X的概率、Y的概率、P(X|Y)进行计算,即建立P(X,Y)的概率分布模型。

b)CRF分词算法:CRF可以看作一个无向图模型,对于给定的标注序列Y和观测序列X,对条件概率P(Y|X)进行定义,而不是对联合概率建模。CRF可以说是目前最常用的分词、词性标注和实体识别算法,它对未登陆词有很好的识别能力,但开销较大

0
回复
C
CF_FC
#70 回复于2020-03

之前还没打完,手误不小心发送了····重新发一遍(老是喜欢按Tab,就跑到“提交回复”Button那里去了)

AI Studio用户名:CF_FC

作业1-1:

(1) 之前已经安装过1.6.3版本的Paddlepaddle,已发截图给班主任。

(2) 学习使用Jieba分词:(分析《背影》一文的词频排行)

# 导入 jieba
import jieba
import jieba.analyse as anls #关键词提取

s=open("D:\\重要文件\\Desktop\\背影.txt").read()
f=open("D:\\重要文件\\Desktop\\分析结果.txt","w+")
for x, w in anls.textrank(s, withWeight=True):
#print('%s %s' % (x, w))
f.write('%s %s \n' % (x, w))
f.close()

结果如下:

父亲 1.0 
看见 0.44607963731616584 
茶房 0.4313917861236198 
铁道 0.2816256008860767 
棉袍 0.2529930385464535 
丧事 0.24840614025141416 
北京 0.23693527297016337 
马褂 0.23420698301594636 
回家 0.22320518727346167 
车门 0.21108605784804502 
不能 0.20904217995296556 
家庭 0.20904217995296556 
桔子 0.20231307114125174 
徐州 0.1951800806206239 
跟着 0.19487616933331287 
打算 0.19384068660419881 
惦记着 0.19093887720623412 
背影 0.18387450240795095 
受凉 0.1831191869952662 
青布 0.18026447601303877 

(3)对人民日报进行切词:

# 导入 jieba
import jieba

Text=''
filename="D:\\XXXX\\1946_05_15_为七百万人民请命.txt"
#打开文件夹,读取内容,并进行分词
with open(filename,'r') as f:
    for line in f.readlines():
        word = jieba.cut(line)
        for i in word:
            final = final + i +"/"
            print(final)

结果如下:(未添加停用词)

为/七百万/人民/请命/
/李庄/
/1946/-/05/-/15/
/第/2/版/(/)/ /专栏/:/
/
/ / /为/七百万/人民/请命/ /李庄/ /一/、/毁灭/与/新生/ /四月/九日/,/五辆/吉普车/载/着/黄河/勘察/团/从/荷泽/出发/,/沿着/黄河/故道/,/由/西南/向/东北/驶去/。/车上/插/着/写/有/“/黄河/”/两字/的/小旗/。/ /“/黄河/要/回来/了/!/”/濮县/的/老百姓/作梦/都/遇到/重新/袭来/的/滔天/黄水/。/恐惧/袭击/着/沿河/几百万/居民/。/ /今年/一年/里/国民党/就/提出/“/黄河/归故/”/。/解放区/因为/这/是/个/关系/几百万/人命/的/大/事情/,/马上/派遣/自己/的/代表/和/国民党/磋商/,/开封/会议/之后/,/由/三方/代表/合组/勘察/团/,/赴/黄河/故道/勘察/,/以/决定/施工/合龙/计划/,/和/救济/的/办法/。/ /吉普车/带/着/神秘/的/消息/驶过/来/。/人们/看见/西装革履/的/国民党/代表/,/他们/更加/惊愕/了/。/他们/知道/这些/人/就是/过去/负责/“/治黄/”/,/贪污/中/饱/而/使/黄河/经常/决口/的/人/。/他们/的/到来/,/只会/给/自己/增加/更/多/的/不幸/。/但是/,/他们/又/看到/了/自己/的/代表/—/—/冀鲁豫/行署/曹心/斋/主任/及/孙明甫/等/,/于是/他们/安心/了/。/他们/请愿/、/他们/哭诉/,/希望/代表/们/能够/看到/这个/近/三十/县/七百万/人/生死攸关/的/大/问题/,/先复/堤浚河/,/再/合龙/放水/,/同时/切实/救济/被害/的/人民/。/他们/知道/国民党/代表/靠不住/,/因此/,/他们/要求/治河/机构/中/一定/要/有/自己/的/代表/。/ /一周/的/勘察/,/给/人/的/印象/是/毁灭/和/新生/。/ /两千里/的/河堤/,/已经/完全/支离破碎/了/,/许多/地方/被/敌伪/挖成/了/封锁/沟/,/许多/地方/被/农民/改成/了/耕地/。/再/加上/风吹雨打/,/使/许多/段/河堤/连/痕迹/都/没有/了/。/黄河水利委员会/委员长/赵守钰/也/说/:/“/百分之三十/的/堤坝/须要/完全/重新/修补/。/”/ /不真/去/看看/黄河/故道/,/很难/想像/它/的/可怕/。/由于/堤坝/的/破坏/,/许多/段/河身/高出/地面/一丈/二到/两丈/,/这种/俗语/所说/的/“/悬河/”/,/全是/过去/统治者/只/治标/、/不/治本/,/徒/斤斤/于/“/九仞/之城/”/的/结果/。/防险/的/石坝/大多/已经/坍塌/,/在/积沙/的/河/身上/,/矗立/着/一座座/骇人/的/淤滩/…/…/。/这样/大/的/工程/,/短期内/是/绝对/不能/完成/的/。/在/冀鲁豫/解放区/内/的/河身/共长/一四/二六/里/,/如果/完全/修好/,/至少/须筑/三千五百/万/土方/,/用/人工/二千/三百三十万/个/—/—/怕人/的/数字/!/ /但是/,/沿着/黄河/故道/走一遭/,/就/同时/能够/看到/民主/政府/和/群众/力量/的/伟大/。/自从/这里/成/了/解放区/,/过去/因/洪水泛滥/而/逃亡/在外/的/人们/都/回来//。/他们/在/民主/政府/领导/与/扶值/下/,/垦荒/植树/,/重新/建立/自己/的/家园/。/现在/广袤/的/河滩/里/,/点缀/起/一片片/油绿/的/麦田/,/麦田/中间/是/被/杨柳树/拱/围着/的/村庄/,/街道/整齐/、/房屋/宽敞/,/显然/是/有/计划/的/建造/起来/的/。/ /东平/州/过去/黄水/为/患/,/语称/“/十年/九不/。/”/自从/黄河/改道/,/这里/建立/了/解放区/以后/,/那种/怕人/的/事情/完全/成为/过去/了/。/冀鲁豫/行署/曾以/十八/万元/专门/治湖/。/三百顷/瘠/硗/的/湖地/变为/良田/,/每亩/可/收获/三百斤/麦子/。/东平湖/与/运河/相连/,/运河/又/与/黄河/相通/,/如果/黄河/重/来/,/这些/湖地/都/将/化为乌有/。/ /利津/东北/近海/的/地方/曾经/全为/荒区/,/荆条/遍地/,/五谷/不生/,/田野/里/到处/奔驰/着/兔子/,/抗战/后/这里/也/成/了/解放区/,/寿光/、/安邱/…/…/的/人/纷纷/赶来/垦荒/。/政府/发放/了/二百六十/万元/垦荒/贷/。/人们/披荆斩棘/,/一面/垦植/,/一面/和/进攻/的/敌人/打仗/。/新/生活/建立/起来/了/,/人口/由/五万/增至/三十万/,/七分/之三/的/人口/过/着/中农/以上/的/生活/。/这里/原先/就/没有/堤坝/,/黄河/归故/之后/,/必致/洪流/漫流/,/这些/流血流汗/、/功在/国家/的/人民/,/又/要/遭逢/流离失所/的/厄运/。/ /“/黄河/归故/”/的/影响/太大/了/,/仅/郓/、/鄄/、/濮/、/寿/、/范/、/昆六县/,/就/将/有/八百/五十六个/村庄/陆沉/水底/,/三/十七万/九千多/人口/,/要/失掉/生命/和/家园/。/ /二/、/天灾/?/人祸/?/ /抗战/胜利/之后/,/三/八年/黄河/在/中牟/花园口/溃决/的/公开/秘密/揭破/了/。/原/是/蒋介石/命令/马/鸿达/掘开/的/。/坚持/一/党专政/的/英雄/们/常/打败仗/原无足奇/,/问题/在于/这些/人们/永远/不/自/悔悟/,/却/以/人民/的/生命财产/作/赌注/。/以至/滚滚/黄河/一泻千里/,/豫东/的/中牟/、/尉氏/及/皖北/的/太和/、/汤阴/等/十六/县/随之/陆沉/。/三十多万/人/死于非命/,/六百万/人/失掉/了/家园/。/人为/的/灾害/等于/消灭/了/一个/比利时/,/死绝/了/一个/卢森堡/。/ /黄河/百害/,/早经载/诸/史籍/。/历代/治黄/,/不知/难倒/了/多少/水利/专家/。/其中/原因/虽多/,/但/最/重要/的/一项/,/是/这种/天灾/始终/与/人祸/相结合/,/二者/并/互为因果/。/从/民国/二年/至/二十三年/,/黄河/在/现/冀鲁豫/解放区/范围/内/决口/达/十二次/,/决口/次数/且/在/按/比例/逐年/增加/。/治黄/被/视作/发财/之道/,/偷工减料/,/苟且/敷衍/,/黄河/不决/,/是/无/“/天理/”/。/沿河/群众/坚持/治河/机构/一定/要/有/解放区/代表/参加/,/就是/这个/缘故/。/从/三/八年/到/四五年/,/决口/指数/更是/飞跃/增加/,/八年/中竟/有/九次/,/每次/均/决口/数处/)/。/而且/都/是/国民党/掘开/的/。/ /国民党/反动派/会/说/:/“/我/在/三/八年/决开/黄河/,/是/为了/阻止/敌人/,/保卫/中原/。/”/中原/是否/因此/保卫/住/了/,/已/为/抗战/中/的/事实/所/证明/,/这里/不去/说/它/,/只/说/以后/的/几次/,/其/目的/竟是/完全/为了/淹没/豫东/坚持/抗战/的/八路军/、/新四军/和/淳朴/的/人民/。/例如/:/ /四/○/年/,/国民党/泛东/游击/支队/阮创部/在/西华/郭村/决口/两处/,/目的/在/淹没/我/十二分/区/淮太西/部队/。/ /四/三年/,/国民党/在/豫东/大/“/剿/”/新四军/,/因为/新四军/有/群众/拥护/,/剿/不了/,/于是/国民党/河南/十二/专署/第三/大队/梁化龙/就/在/古铜/、/刘口/等/地/决口/十三处/,/企图/使/我/抗战/军民/同归于尽/。/ /四四年/,/国民党/泛东/挺进/军张/公达/掘开/扶沟/陵口/,/把/豫东/人民/及/我军/已/播种/的/田地/完全/淹没/,/企图/把/我们/饿死/。/ /四五年/九月/四日/,/国民党/泛东/挺进/军/曹世部/掘开/水波/口/,/滚滚/黄河/向/我/反攻/大军/汹涌/而/来/,/这时/我/已/解放/扶沟/,/正向/鄢陵/挺进/(/鄢陵/城内/住/的/是/伪军/)/。/被/洪水/阻绝/了/我军/的/进路/。/ /四五年/九月/二十五日/,/国民党/泛东/“/剿共/”/独立/支队/马淮诚/决开/西华/以东/清河/驿堤/,/这时/我军/正/布置/收复/太康/,/洪水/造成/一片/阻绝/地带/,/给/我军/增加/了/许多/困难/。/ /这些/决口/给予/豫东/抗战/军民/的/损失/,/恐怕/永远/也/算不清/的/。/这次/国民党/要/“/黄河/归故/”/的/目的/,/是/在/把/山东/、/豫东/、/苏中/、/苏北/等/解放区/与/华北/分割/开来/,/是/国民党/全面/内战/阴谋/的/一部分/。/ /三/、/问题/的/焦点/ /解放区/民主/政府/和/广大/人民/深知/“/黄河/归故/”/将/带给/他们/什么/。/但是/他们/并/没有/反对/“/黄河/归故/”/。/ /体念/黄泛区/人民/的/痛苦/,/他们/默默无言/的/承受/了/“/黄河/归故/”/这/副/沉重/的/担子/。/问题/在于/怎么/个/“/归/”/法/。/ /四月/十五日/,/国民党/、/解放区/及/美方/代表/在/荷泽/成立/了/协议/,/规定/先浚河/修堤/、/后/合龙/放水/;/由/黄/委会/呈请/联/总行/总/切实/救济/沿河/难胞/,/每人/发给/十万元/(/法币/)/迁移费/,/治河/机构/由/国民党/、/解放区/双方/代表/共同/组成/。/ /但是/,/荷泽/协议/墨迹未干/,/国民党/就/撕毁/了/这/一/协定/。/也许/,/在/订定/这个/协议/时/它/就/没有/准备/实行/。/它/的/宣传/机关/中央社//:/“/复堤/工作/已/与/共方/商定/,/可于/两/月/内/配合/花园口/堵口/工作/同时/完成/。/”/这/是/瞪/着/眼睛/造谣/,/明眼人/一看/便/知/,/不但/双方/并未/这么/“/商定/”/,/而且/像/这样/浩大/的/浚/河复堤/工作/,/本/年内/根本/不能/完成/。/中央社/是/一贯/诬蔑/解放区/的/,/在/这时候/它/却说/:/“/中共/区/民众/有/组织/,/有/庞大/的/人力物力/”/,/但是/“/阻挠/河工/之/进行/。/”/这/显然/是/企图/率/甚/河水/的/借口/。/ /解放区/代表/赵明甫氏/看到/这种/情形/,/特/亲自/到/花园口/跑/了/一遭/,/又/和/国民党/代表/会谈/,/商定/故道/下游/于/麦收/前先/测量/河床/,/秋后/浚河/并/裁沟/取道/,/明春/修理/险工/,/最后/再/合龙/放水/。/但是/,/惯于/自食其言/的/国民党/马上/又/变/了/卦/,/它/顽固/的/坚持/要/在/两个/月/内/全部/完工/。/ /与其说/国民党/从来/不管/人民/的/死活/,/无宁/说/它/的/一举一动/,/都/是/有意/制/人民/于/死命/。/故道/的/复堤/浚/河/工程/虽离/完成/尚远/,/但/花园口/的/堵口/工程/却/已/差不多/了/。/这个/一千六百/公尺/的/决口/,/连续/从/两边/“/抢修/”/,/中间/只/剩/了/六百/公尺/尚未/合龙/。/民国/以来/历次/黄河/决口/,/总是/丰年/合龙/,/甚至/有/迟/至/第三年/者/。/那/时候/国民党/迟迟/其行/,/这次/却/特别/积极/了/。/它们/调来/汽车/,/修/了/铁路/,/残酷/的/鞭打/着/强拉来/的/民夫/,/无限/止/的/强征/各种/材料/。/为的是/尽早/放过/水来/,/使/沿河/的/解放区/变成/泽国/。/ /花园口/合龙/之/日/,/差不多/正是/大泛/之时/,/滔天/的/黄水/就要/横流/过来/,/几百万/条/生命/将要/被/抛/到/到/死亡线/上/。/ /面临/着/这个/天大/的/阴谋/,/又/一个/“/比利时/”/将/被/毁灭/了/。/ /全国/人民/警惕/起来/,/拯救/这/七百万/将/被/毁灭/的/同胞/!/ /河南/、/河北/、/山东/的/人民/动员/起来/,/坚持/彻底/实现/荷泽/协议/,/用/自己/的/力量/维护/自己/的/生命/!/

计算概率:

# 导入 jieba
import jieba
import pandas as pd

Text=[]
filename="D:\\XXXX\\1946_05_15_为七百万人民请命.txt"

with open(filename,'r') as f:
    for line in f.readlines():
        word = jieba.cut(line)
        Text.extend(list(word))
Text=pd.Series(Text)
word_prob=Text.value_counts(normalize=True)
print(word_prob)

计算信息熵:

import math
H=0
for a,b in word_prob.items():
    b = b/len(Text)
    p=b
    H=H+p*math.log(p,2)
H=-H
print("信息熵:",H)

结果如下:

信息熵: 0.010102403927983734

作业1-2:

(1)O(NM^2)

(2)Jieba分词当中,全模式就会给出全部的分词候选。

(3)后向最大匹配法,双向最大匹配法

0
回复
prepared
#71 回复于2020-03

PS: 上一个回复无效。

AI Studio用户名:18801936053

作业1-1

(1)下载飞桨本地并安装成功,将截图发给班主任

已经把安装图片发给班主任。

(2)学习使用PaddleNLP下面的LAC模型或Jieba分词

学习jieba模型:

jieba 是目前最好的 Python 中文分词组件,它主要有以下 3 种特性:

支持 3 种分词模式:

  • 精确模式
  • 全模式
  • 搜索引擎模式
  • 支持繁体分词
  • 支持自定义词典

使用jieba进行分词练习,获取人民日报1946年05月的全部分词结果:

    def getCorpus(self, rootDir):
        corpus = []
        r1 = u'[a-zA-Z0-9’!"#$%&\'()*+,-./::;<=>?@,。?★、…【】《》?“”‘’![\\]^_`{|}~]+'  # 用户也可以在此进行自定义过滤字符
        for file in os.listdir(rootDir):
            path  = os.path.join(rootDir, file)
            if os.path.isfile(path):
                # 打印文件地址
                #print(os.path.abspath(path))
                # 获取文章内容,fromfile主要用来处理数组 pass
                # filecontext = np.fromfile(os.path.abspath(path))
                with open(os.path.abspath(path), "r", encoding='utf-8') as file:
                    filecontext = file.read();
                    #print(filecontext)
                    # 分词 去掉符号
                    filecontext = re.sub(r1, '', filecontext)
                    filecontext = filecontext.replace("\n", '')
                    filecontext = filecontext.replace(" ", '')
                    seg_list = jieba.lcut_for_search(filecontext)
                    corpus += seg_list
                    #print(seg_list)
                    #print("[精确模式]:" + "/".join(seg_list))
            elif os.path.isdir(path):
                TraversalFun.AllFiles(self, path)
        return corpus
 

(3)对人民日报语料完成切词,并通过统计每个词出现的概率TF,计算信息熵 语料地址:

https://github.com/fangj/rmrb/tree/master/example/1946%E5%B9%B405%E6%9C%88

3.1 计算每个词的TF以及信息熵

输出结果:

数据集大小,size: 163039

    #构造词典,统计每个词的频率,并计算信息熵
    def calc_tf(corpus):
        #   统计每个词出现的频率
        word_freq_dict = dict()
        for word in corpus:
            if word not in word_freq_dict:
                word_freq_dict[word] = 1
            word_freq_dict[word] += 1
        # 将这个词典中的词,按照出现次数排序,出现次数越高,排序越靠前
        word_freq_dict = sorted(word_freq_dict.items(), key=lambda x:x[1], reverse=True)
        # 计算TF概率
        word_tf = dict()
        # 信息熵
        shannoEnt = 0.0
        # 按照频率,从高到低,开始遍历,并未每个词构造一个id
        for word, freq in word_freq_dict:
            # 计算p(xi)
            prob = freq / len(corpus)
            word_tf[word] = prob
            shannoEnt -= prob*log(prob, 2)
        print(len(word_freq_dict))
        return word_tf, shannoEnt

信息熵:14.047837802885464

作业1-2

(1)思考一下,假设输入一个词表里面含有N个词,输入一个长度为M的句子,那么最大前向匹配的计算复杂度是多少?

所以总复杂度: O(N*M^2)

for index in range(M):
        for i in range(index+1):
            #判断词典中有没有这个词,时间复杂度是N

(2)给定一个句子,如何计算里面有多少种分词候选,你能给出代码实现吗?

2^(n-1)

n为句子长度

def cut_num(input_str_len):
        '''
        :param input_str_len: 句子长度
        :return:
        '''
    
        if(input_str_len == 1):
            return 1
        elif(input_str_len == 2):
            return 2
        else:
            return 2 * cut_num(input_str_len-1)
    
    print(str(cut_num(4)))

(3)除了最大前向匹配和N-gram算法,你还知道其他分词算法吗,请给出一段小描述。

  • 基于词表的分词方法
  1. 正向最大匹配法(forward maximum matching method, FMM)
  2. 逆向最大匹配法(backward maximum matching method, BMM)
  • N-最短路径方法
  1. 基于统计模型的分词方法
  2. 基于N-gram语言模型的分词方法
  • 基于序列标注的分词方法
  1. 基于HMM的分词方法
  2. 基于CRF的分词方法
  3. 基于词感知机的分词方法
  4. 基于深度学习的端到端的分词方法
0
回复
凌烟阁主人
#72 回复于2020-03

AI Studio用户名: 凌烟阁主人

作业1-1:

(1) 截图已发送

(2)学习jieba分词

(3)对人民日报语料example中语料进行分词,统计词个数,及信息熵

0
回复
凌烟阁主人
#73 回复于2020-03

AI Studio用户名: 凌烟阁主人

作业1-2:

(1)思考一下,假设输入一个词表里面含有N个词,输入一个长度为M的句子,那么最大前向匹配的计算复杂度是多少?
最坏情况,每个字都再词表中,那么每个都需要比较,从后向前,依次和词表里N个词进行比较,那么应该是N*(m(m+1)/2)
复杂度为o(N*M^2)

# (2)给定一个句子,如何计算里面有多少种分词候选,你能给出代码实现吗?
# 最多的分词候选,那么基于最大前向匹配算法,从后到前,每匹配上1词,算1个。通过递归实现
input_str_len = 4
def cut_num(input_str_len):
if(input_str_len == 1):
return 1
elif(input_str_len == 2):
return 2
else:
return 2 * cut_num(input_str_len-1)
print(str(cut_num(input_str_len)))

jieba中采用全搜索模式即可

(3)除了最大前向匹配和N-gram算法,你还知道其他分词算法吗,请给出一段小描述。
基于词表的分词方法
正向最大匹配法(forward maximum matching method, FMM)
逆向最大匹配法(backward maximum matching method, BMM)
N-最短路径方法
基于统计模型的分词方法
基于N-gram语言模型的分词方法
基于序列标注的分词方法
基于HMM的分词方法
基于CRF的分词方法
基于词感知机的分词方法
基于深度学习的端到端的分词方法

0
回复
vortual
#74 回复于2020-03

AI Studio用户名:vortual

作业2-1附加题:使用词库进行推理,代码如下

with fluid.dygraph.guard():
    a = 'king'
    b = 'queen'
    c = 'man'
    k = 10
    embedding_size = 200
    model = SkipGram("skip_gram_model", vocab_size, embedding_size)
    params_file_path = './skip_gram_epoch2'
    model_state_dict, _ = fluid.load_dygraph(params_file_path)
    model.load_dict(model_state_dict)
    W = model.embedding._w.numpy()
    x1 = W[word2id_dict[a]]
    x2 = W[word2id_dict[b]]
    
    y1 = W[word2id_dict[c]]
    x = y1 - x1 + x2
    
    cos = np.dot(W, x) / np.sqrt(np.sum(W * W, axis=1) * np.sum(x * x) + 1e-9)
    flat = cos.flatten()
    indices = np.argpartition(flat, -k)[-k:]
    indices = indices[np.argsort(-flat[indices])]
    for i in indices:
        print('for "%s - %s = %s - ?", the similar word is %s' % (a, b, c, str(id2word_dict[i])))

运行结果:

for "king - queen = man - ?", the similar word is man
for "king - queen = man - ?", the similar word is queen
for "king - queen = man - ?", the similar word is woman
for "king - queen = man - ?", the similar word is devil
for "king - queen = man - ?", the similar word is she
for "king - queen = man - ?", the similar word is lady
for "king - queen = man - ?", the similar word is girl
for "king - queen = man - ?", the similar word is haired
for "king - queen = man - ?", the similar word is blonde
for "king - queen = man - ?", the similar word is lemmy
0
回复
huahua
#75 回复于2020-03

AI Studio用户名:huahua

 作业1-1

(1)

(2)

(3)

作业1-2

(1)和(2)

(3)

 

 

0
回复
多佛朗mingle
#76 回复于2020-03

AI Studio用户名:多佛朗mingle

作业2-1附加题:对embedding进行降维聚类可视化分析

代码如下:

效果如下

可以看到one,two,three等这些数字聚到一起,mouse,desktop,windows,chip这些电脑相关的词聚到一起,desk,chairs这些家具相关的词聚到一起,he,she,they这些人称代词聚到一起

0
回复
3
3626969
#77 回复于2020-03

2月25日第一次作业
AI Studio用户名:赵杭天

此回答也放在个人网站上https://willtian.cn/?p=864

(因github账号只能登入aistudio而无法登入社区论坛,所以回答使用的是百度账号)

作业1-1:
(1)下载飞桨本地并安装成功,将截图发给班主任:


(2)学习使用PaddleNLP下面的LAC模型或Jieba分词
LAC模型,安装并测试成功:


(3)对人民日报语料完成切词,并通过统计每个词出现的概率,计算信息熵
使用Jieba分词:

删除因.MD格式而出现的符号,并使用/作为分隔符以实现并行处理,最终结果:

文本文件数:447,不同词的数量:21758,总词数:172731,信息熵:7.467906

作业1-2
(1)思考一下,假设输入一个词表里面含有N个词,输入一个长度为M的句子,那么最大前向匹配的计算复杂度是多少?

       最坏的情况:词表所有的词都没有出现在句子里,句子被判定为当前未处理句子长度(记为S1_len)个单字,图解如下:

所以,总的比较次数=N*(M-1+2)*(M-1)/2=N*(M^2-1)/2,复杂度为O(N*M^2) 。

 

(2)给定一个句子,如何计算里面有多少种分词候选,你能给出代码实现吗?

 

(3)除了最大前向匹配和N-gram算法,你还知道其他分词算法吗,请给出一段小描述。

【基于深度学习的端到端的分词方法】

最近,基于深度神经网络的序列标注算法在词性标注、命名实体识别问题上取得了优秀的进展。词性标注、命名实体识别都属于序列标注问题,这些端到端的方法可以迁移到分词问题上,免去CRF的特征模板配置问题。但与所有深度学习的方法一样,它需要较大的训练语料才能体现优势。

BiLSTM-CRF的网络结构如上图所示,输入层是一个embedding层,经过双向LSTM网络编码,输出层是一个CRF层。下图是BiLSTM-CRF各层的物理含义,可以看见经过双向LSTM网络输出的实际上是当前位置对于各词性的得分,CRF层的意义是对词性得分加上前一位置的词性概率转移的约束,其好处是引入一些语法规则的先验信息。

从数学公式的角度上看:

其中,A是词性的转移矩阵,P是BiLSTM网络的判别得分。

因此,训练过程就是最大化正确词性序列的条件概率P(y|X),似的工作还有LSTM-CNNs-CRF:

在后续的课程中我们可能还会遇到。

0
回复
取个啥好的名字
#78 回复于2020-03

AI Studio用户名:取个啥好的名字

作业1-1:

(1)python3.8目前无法安装paddlepaddle,安装3.7后可以通过pip安装,已经将图发给班主任

(2)LAC分词模型学习

import paddlehub as hub

module = hub.Module(name="lac")
test_text = ["我今天想学习深度学习课程", "我从AIStudio中,学到了很多知识"]
inputs = {"text": test_text}
results = module.lexical_analysis(data=inputs)

for result in results:
    print(result)


输出结果为:

[2020-03-01 16:36:23,550] [ INFO] - Installing lac module
[2020-03-01 16:36:23,565] [ INFO] - Module lac already installed in /home/aistudio/.paddlehub/modules/lac
[2020-03-01 16:36:23,621] [ INFO] - 20 pretrained paramaters loaded by PaddleHub
{'word': ['我', '今天', '想', '学习', '深度', '学习', '课程'], 'tag': ['r', 'TIME', 'v', 'vn', 'n', 'vn', 'n']}
{'word': ['我', '从', 'AIStudio', '中', ',', '学到', '了', '很多', '知识'], 'tag': ['r', 'p', 'n', 'f', 'w', 'v', 'u', 'a', 'n']}


jieba分词学习代码为:

!pip install jieba
import jieba
import jieba.posseg as pseg
jieba.enable_paddle()# 启动paddle模式。 0.40版之后开始支持,早期版本不支持
test_text = ["我今天想学习深度学习课程", "我从AIStudio中,学到了很多知识"]
for str in test_text:
    seg_list = pseg.cut(str,use_paddle=True) # 使用paddle模式
    print(20*"*")
    print(str)
    for word, flag in seg_list:
        print("word:",word,"flag:",flag)


结果为:

Paddle enabled successfully......
2020-03-01 16:39:05,338-DEBUG: Paddle enabled successfully......
********************
我今天想学习深度学习课程
word: 我 flag: r
word: 今天 flag: TIME
word: 想 flag: v
word: 学习 flag: vn
word: 深度 flag: n
word: 学习 flag: v
word: 课程 flag: n
********************
我从AIStudio中,学到了很多知识
word: 我 flag: r
word: 从 flag: p
word: AIStudio flag: ns
word: 中 flag: f
word: , flag: v
word: 学到 flag: v
word: 了 flag: u
word: 很多 flag: a
word: 知识 flag: n


(3)语料分析代码

import os
import paddlehub as hub
import numpy as np
module = hub.Module(name="lac")
path = '194605'
wordcount = {}
typecount = {}
for file in os.listdir(path):
    news = open(os.path.join(path,file),'r')
    text = []
    for line in news.readlines():
        text.append(line)
    res = module.lexical_analysis(data={'text':text})
    for r in res:
        for word in r['word']:
            if word in wordcount.keys():
                wordcount[word] += 1
            else:
                wordcount[word] = 1
        for tag in r['tag']:
            if tag in typecount.keys():
                typecount[tag] += 1
            else:
                typecount[tag] = 1
totalcount = sum(wordcount.values())
wordShannonEnt = 0
typeShannonEnt = 0
for i in wordcount.values():
    fraction = i/totalcount
    wordShannonEnt += fraction*np.log2(fraction)
for i in typecount.values():
    fraction = i/totalcount
    typeShannonEnt += fraction*np.log2(fraction)
print(wordShannonEnt,typeShannonEnt)


输出结果分别为分词信息熵和类型信息熵

-10.593007506993564 -3.592578118931914


作业1-2:

(1)最大前向匹配,按照最坏打算,单个字才能匹配成功,则第一个字的匹配成功最坏所需次数为NM,第二个字为N(M-1),一次类推总共需要N*(M+M-1+M-2+...+2+1)=N*(M*(M+1)/2), 时间复杂度为O(N*M^2)

(2)假设测试的句子为“我今天想学习一下深度学习课程”,可能存在的候选词有[我,今,天,今天,想,学,习,学习,一,一下,深度,课,课程],则代码为:

text = "我今天想学习一下深度学习课程"
text_dict = ["我","今","天","今天","想","学","习","学习","一","一下","深度","课","课程"]
def text_count(text, word, dict):
    if len(word) == 0:
        print('/'.join(text))
        return 1
    count = 0
    for i in range(1, len(word) + 1):
        if word[:i] not in dict:
            continue
        count += text_count(text + [word[:i]], word[i:], dict)
    return count
candidate = text_count([], text, text_dict)
print("候选数:", candidate)


结果为:

我/今/天/想/学/习/一下/深度/学/习/课程
我/今/天/想/学/习/一下/深度/学习/课程
我/今/天/想/学习/一下/深度/学/习/课程
我/今/天/想/学习/一下/深度/学习/课程
我/今天/想/学/习/一下/深度/学/习/课程
我/今天/想/学/习/一下/深度/学习/课程
我/今天/想/学习/一下/深度/学/习/课程
我/今天/想/学习/一下/深度/学习/课程
候选数: 8


(3)对于分词算法,搜索知识之前并不清楚相关的分词算法,通过网络学习,个人认为分词算法可以分为两大类:

一、通过构建词典,最够依据匹配进行分词主要的算法有:

最大匹配分词:就是先构建词树,然后通过最长分词对句子一次进行分割判断,然后比对

最短路径分词:先将句子中所有可能存在的词进行标注,然后利用两点之间的最短路径也包含了路径上其他顶点间的最短路径,这一性质,通过贪心算法或动态规划,选出最佳的分词方案

N-gram算法:主要是将词出现的频率加入其中,也就是首先对各个分词出现的概率进行建模,加入到最短路径分词的算法中。

二、基于字的分词,主要是将分词看作,每个字的标注问题,将一个字标记成B(Begin), I(Inside), O(Outside), E(End), S(Single)。这样可以利用机器学习和深度学习,通过输入值当前字和其上下文,判断该字所属分类。其下有很多分类还在学习,大家有兴趣可以搜搜看,我也不知道作业让不让补外链

0
回复
FrankFly
#79 回复于2020-03

AI Studio用户名:你还说不想我吗

作业1-1:

1.paddle安装

2 paddle hub 和jieba安装


3 人民日报语料切词,计算信息熵

import jieba
import os
import paddlehub as hub
module = hub.Module(name="lac")
rmrb_dir = 'D:\\Study\\01Data\\dataset\\nlp\\rmrb\\example\\1946年05月'
rmrb=[]
for file_name in os.listdir(rmrb_dir):
    file_path = os.path.join(rmrb_dir,file_name)
#     print(file_path)
   
    with open(file_path,'r',encoding='utf-8') as f:
        file_raw = f.read()
        file_context = file_raw.split('专栏:')[1][4:]
        file_context = ''.join([line.strip() for line in file_context.split('\n')])
        rmrb.append(file_context)
segs = module.lexical_analysis(data={'text':rmrb})

words=[]
for seg in segs:
    words.extend(seg['word'])
print(len(words))

#获取停用词表
stopfile1 = 'CNstopwords.txt'

with open(stopfile1, 'r', encoding='utf-8') as f:
    stopwords = f.read().split("\n")

def get_freq(words,stopwords=None):
    word_freq={}
    for word in words:
        if word not in stopwords:
            if word in word_freq:
                word_freq[word] = word_freq[word] + 1
            else:
                word_freq[word] = 1
    return word_freq
import numpy as np
def cal_entropy(freqlist):
    '''calculate entropy of plist , list type
    '''
    freqs = np.array(freqlist)
    p = freqs / freqs.sum()
    entropy = np.sum(-p*np.log2(p))
    return entropy

word_freq = get_freq(words,stopwords=stopwords)
freqlist = list(word_freq.values())
cal_entropy(freqlist)
分词库 Paddle-lac jieba
词典Size(去停用词) 21396 20721
信息熵 12.702 12.631
频次 top 100


作业1-2

(1)思考一下,假设输入一个词表里面含有N个词,输入一个长度为M的句子,那么最大前向匹配的计算复杂度是多少?

假设词典中词的最大长度也为M,从句子M开始匹配,匹配N次,未找到,从[0,M-1]开始匹配,匹配N次,最坏情况下,单字匹配,(M+(M-1)+(M-2),……3+2+1)N=M(M+1)N/2,复杂度为O(NM^2)

(2)给定一个句子,如何计算里面有多少种分词候选,你能给出代码实现吗?

给定包括该句子所有可能的词的词典,进行最大前向遍历;

sentence ='他说的确实在理'
worddict = ['他', '说','的', '的确', '确实', '实在', '理', '在理','在']
def list_segment(result, sentence, worddict):
  '''result:分词时的中间列表
  sentence: 待分词句子
  worddict:分词词典
  '''
  cnt = 0
  if len(sentence) == 0:
      print("/".join(result))
      return 1   
  for i in range(1, len(sentence)+1):
      if sentence[:i] in worddict:
          cnt += list_segment(result+[sentence[:i]], sentence[i:], worddict)
  return cnt
cnt =list_segment([],sentence,worddict)
print('候选分词可能数目:%d' % cnt)
​
out:
他/说/的/确实/在/理
他/说/的/确实/在理
他/说/的确/实在/理
候选分词可能数目:3


(3)除了最大前向匹配和N-gram算法,你还知道其他分词算法吗,请给出一段小描述。

分词算法可分为三类,基于词典的匹配算法,基于标注数据的机器学习算法,基于深度学习的算法。

1. 基于词典的匹配算法,有最大前向匹配,最大逆向匹配,双向匹配等,速度相对标注模型快,缺点是不能发现新词;

2. 基于标注数据的机器学习算法有隐马尔可夫模型和条件随机场模型,这两种算法都能发现新词;

3. 基于深度学习的算法,端到端的分词模型,使用WordEmbedding,LSTM,及CRF构造网络,基于大量标注语料训练而来,准确度相比传统算法更高。

一些开源算法的性能比较 https://github.com/thunlp/THULAC-Python,ltp,ICTCLAS,jieba,thulp中 jieba速度最快。

0
回复
l
lzytucker
#80 回复于2020-03

AI Studio用户名:lzytucker

作业1-1

(1)截图发班主任

(2)

(3)

作业1-2

(1)使用最大向前匹配算法切词时,词表里面含有N个词则进行N轮循环,而一轮循环下又有循环,最大循环次数为M(句子长度),因此时间复杂度用大O表示法可以表示为O(NM)。

(2)采用结巴切词的搜索引擎模式。

seg_list = jieba.cut_for_search("小明硕士毕业于中国科学院计算所,后在日本京都大学深造") # 搜索引擎模式

(3)前向最大匹配算法:从前向后寻找在词典中存在的词。

后向最大匹配算法:与前向最大匹配算法类似,只是方向相反,即从后向前寻找词典中存在的词并输出。

双向最大匹配算法:双向最大匹配算法的原理就是将正向最大匹配算法和逆向最大匹配算法进行比较,从而确定正确的分词方法。

0
回复
Action
#81 回复于2020-03

AI Studio用户名:Action

作业1-1

(1)下载飞桨本地并安装成功,将截图发给班主任

(2)学习使用PaddleNLP下面的LAC模型或Jieba分词

(3)对人民日报语料完成切词,并通过统计每个词出现的概率,计算信息熵

作业1-2 

(1)思考一下,假设输入一个词表里面含有N个词,输入一个长度为M的句子,那么最大前向匹配的计算复杂度是多少?

O(N*M^2)

(2)给定一个句子,如何计算里面有多少种分词候选,你能给出代码实现吗?

(3)除了最大前向匹配和N-gram算法,你还知道其他分词算法吗,请给出一段小描述。
基于深度学习的端到端的分词方法:输入层是一个embedding层,经过双向LSTM网络编码,输出层是一个CRF层

 

0
回复
在@后输入用户全名并按空格结束,可艾特全站任一用户