【问题标题】:Ruby Meaningful Words -- Remove StopwordsRuby 有意义的词——删除停用词
【发布时间】:2015-03-04 04:24:45
【问题描述】:

我有一组语音文件,我需要与一组停用词进行比较以删除停用词并留下剩余的有意义的单词。

到目前为止,我有这样的事情:

stopwords = File.readlines('PATH TO TXT FILE')
speeches = []

Dir.glob('PATH TO ALL SPEECHES').each do |speech|
    #code to read each speech and store into an array
    f = File.readlines(speech)
    speeches << f
end

lincolnSpeech = speeches[0]

def process_file(file_name)
    all_words = file_name.scan(/\w+/)
    meaningful_words = all_words.select { |word| !stopwords.include?(word) }
    return meaningful_words
end

我将此函数的结果嵌入到我的 HTML 中,如下所示:

<ul>
      <li><pre style="white-space: pre-wrap;word-wrap: break-word">#{process_file(lincolnSpeech)}</pre></li>
</ul>

但这会破坏页面并导致我的 HTML 完全消失。我已将问题缩小到函数中的行:

meaningful_words = all_words.select { |word| !stopwords.include?(word) }

而这条线是罪魁祸首。我不确定为什么它会破坏我的代码。也许其中的一部分已被弃用?谁能提供一些关于为什么这不起作用的想法,以及实现我想要的效果的替代方法?

【问题讨论】:

    标签: ruby nlp stop-words


    【解决方案1】:

    我真的很惊讶您在 scan 调用中没有收到 NoMethod 错误。 File.readlines 返回一个字符串数组,所以传递给process_filelincolnSpeech 是一个数组,我认为数组没有scan 方法。

    假设您的停用词在该文件中是每行一个,我会这样做:

    require 'set'
    # Finding an item in a Set will be faster than finding one in
    # an array, especially if the array is large.
    stopwords = Set.new(File.readlines('PATH TO TXT FILE'))
    
    speech_files = Dir.glob('PATH TO ALL SPEECHES')
    
    lincoln_speech = speech_files[0]
    
    def process_file(file_name)
      speech_words = File.read(file_name).split # get each word in file
      speech_words.reject { |word| stopwords.include?(word) }.join(' ') # reject stopwords and glue it back together
    end
    

    有几个潜在的大问题 - 一个是没有参数的 split 调用有点幼稚,并且会在拆分的单词中包含标点符号,就像这样。

    "Well, space is there, and we're going to climb it,".split
    # => ["Well,", "space", "is", "there,", "and", "we're", "going", "to", "climb", "it,"]
    

    注意单词后面的逗号。使用split(/\W+/) 是部分解决方案,但它会将"we're" 拆分为["we", "re"]

    另一个问题是join(' ') 假设每个单词都用空格分隔,而有些单词可能已经用换行符分隔。对于简单的输入,我发送的内容应该可以很好地工作,但如果您正在处理相当复杂的演讲,您可能需要稍微清理一下您的输入以完成此操作。

    【讨论】:

    • 你知道吗,在 Ruby 中,当你有一个数组数组时,例如:arr = [[1, 2], [2, 3], [3, 4]],你可以像这样puts 嵌入数组项(显而易见的方式):arr.each { |sub_array| puts sub_array[0], sub_array[1] }但是 Ruby 非常聪明,可以让您执行以下操作:arr.each { |left, right| puts left, right }。老实说-我没有运行问题中的代码,但也许有可能,在处理File.readlines 时,Ruby 足够聪明,可以正确应用scan ?我只是假设所有代码都能正常工作,但@amoeboar 缩小到的那个。
    • @PawełDawczak 我确实知道这一点,但提供的代码似乎并非如此。调用 scan 的数组出现 NoMethod 错误 :) gist.github.com/alexcavalli/aeb4840a36a1ea289841
    • 嘿@alexcavalli,你花了一些时间重新实现解决方案真是太好了!感谢您发现了不同的错误,因此我删除了我的答案,因为它无关紧要!干杯!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2016-05-21
    • 1970-01-01
    • 1970-01-01
    • 2023-03-04
    • 2021-02-02
    • 1970-01-01
    • 2018-09-28
    相关资源
    最近更新 更多