计算每个字母的单词数量

PH *_*cia 3 julia

Think Julia一书中,我编写了以下代码来计算每个字母的字数:

abc = "abcdef"
letter_count = 0
fin = open("words.txt")
for letter in abc
    for line in eachline(fin)
        if letter in line
            global letter_count += 1
        end
    end
    println("$letter has $letter_count")
    global letter_count = 0
end
Run Code Online (Sandbox Code Playgroud)

但是,代码只计算字母'a'的出现次数.我无法理解为什么这段代码失败了.

它返回:

56613 have a
0 have b
0 have c
0 have d
0 have e
0 have f
Run Code Online (Sandbox Code Playgroud)

Bog*_*ski 5

你有一个错误的循环顺序(即外循环应该迭代字母).你可以像这样修复它(我也简化了一些代码):

for letter in "abcdef"
    letter_count = count(x -> letter in x, eachline("words.txt"))
    println("$letter has $letter_count")
end
Run Code Online (Sandbox Code Playgroud)

但是,像这样迭代words.txt文件会更快:

let counts = zeros(Int, 6)
    for line in eachline("words.txt")
        for (i, letter) in enumerate("abcdef")
            counts[i] += letter in line
        end
    end
    counts
end
Run Code Online (Sandbox Code Playgroud)

您也可以使用这样的广播来实现所需的结果(我报告它,因为我发现它是一个有趣的解决方案):

julia> letters = "abcdef"
"abcdef"

julia> sum(in.(hcat(letters...), eachline("words.txt")), dims=1)
1×6 Array{Int64,2}:
 56613  16305  30466  30648  76168  11277
Run Code Online (Sandbox Code Playgroud)

编辑:

之间的差eachline(fin)eachline("words.txt")如下:

  • eachline("words.txt") 每次调用时打开(并在完成时关闭)新流;
  • eachline(fin) 使用相同的流,这意味着在迭代的第一个循环结束后,我们在流的末尾,没有任何东西可以在其中读取.

eachline(fin)如果在每次迭代后移动到流的开头,则可以保留该方法,如下所示:

abc = "abcdef"
letter_count = 0
fin = open("words.txt")
for letter in abc
    for line in eachline(fin)
        if letter in line
            global letter_count += 1
        end
    end
    println("$letter has $letter_count")
    global letter_count = 0
    seekstart(fin)
end
close(fin)
Run Code Online (Sandbox Code Playgroud)

请注意,我在您的代码中添加了一个重要的行(并且还添加了,close(fin)因为您应该始终关闭打开的流).但是,至少对我来说,这不是一个非常干净的方法,所以我不想首先推荐它.