第2章: UNIXコマンド¶
popular-names.txtは、アメリカで生まれた赤ちゃんの「名前」「性別」「人数」「年」をタブ区切り形式で格納したファイルである。以下の処理を行うプログラムを作成し、popular-names.txtを入力ファイルとして実行せよ。さらに、同様の処理をUNIXコマンドでも実行し、プログラムの実行結果を確認せよ。
10. 行数のカウント¶
ファイルの行数をカウントせよ。確認にはwcコマンドを用いよ。
with open("../data/popular-names.txt", "r") as f:
lines = f.readlines()
print(len(lines))
2780
# brew install tlrc
# tldr wc
!wc -l ../data/popular-names.txt
2780 ../data/popular-names.txt
11. 先頭からN行を出力¶
ファイルの先頭N行だけを表示せよ。例えば、N=10として先頭10行を表示せよ。確認にはheadコマンドを用いよ。
def print_head(path: str, n: int):
with open(path, "r") as f:
lines = f.readlines()
for l in lines[:n]:
print(l, end="")
print_head("../data/popular-names.txt", 10)
Mary F 7065 1880 Anna F 2604 1880 Emma F 2003 1880 Elizabeth F 1939 1880 Minnie F 1746 1880 Margaret F 1578 1880 Ida F 1472 1880 Alice F 1414 1880 Bertha F 1320 1880 Sarah F 1288 1880
!head -10 ../data/popular-names.txt
Mary F 7065 1880 Anna F 2604 1880 Emma F 2003 1880 Elizabeth F 1939 1880 Minnie F 1746 1880 Margaret F 1578 1880 Ida F 1472 1880 Alice F 1414 1880 Bertha F 1320 1880 Sarah F 1288 1880
12. 末尾のN行を出力¶
ファイルの末尾N行だけを表示せよ。例えば、N=10として末尾10行を表示せよ。確認にはtailコマンドを用いよ。
def print_tail(path: str, n: int):
with open(path, "r") as f:
lines = f.readlines()
for l in lines[-n:]:
print(l, end="")
print_tail("../data/popular-names.txt", 10)
Liam M 19837 2018 Noah M 18267 2018 William M 14516 2018 James M 13525 2018 Oliver M 13389 2018 Benjamin M 13381 2018 Elijah M 12886 2018 Lucas M 12585 2018 Mason M 12435 2018 Logan M 12352 2018
!tail -10 ../data/popular-names.txt
Liam M 19837 2018 Noah M 18267 2018 William M 14516 2018 James M 13525 2018 Oliver M 13389 2018 Benjamin M 13381 2018 Elijah M 12886 2018 Lucas M 12585 2018 Mason M 12435 2018 Logan M 12352 2018
13. タブをスペースに置換¶
ファイルの先頭10行に対して、タブ1文字につきスペース1文字に置換して出力せよ。確認にはsedコマンド、trコマンド、もしくはexpandコマンドなどを用いよ。
with open("../data/popular-names.txt", "r") as f:
lines = f.readlines()
for l in lines[:10]:
print(" ".join(l.split(" ")), end="")
Mary F 7065 1880 Anna F 2604 1880 Emma F 2003 1880 Elizabeth F 1939 1880 Minnie F 1746 1880 Margaret F 1578 1880 Ida F 1472 1880 Alice F 1414 1880 Bertha F 1320 1880 Sarah F 1288 1880
!head -10 ../data/popular-names.txt | sed 's/ / /g'
Mary F 7065 1880 Anna F 2604 1880 Emma F 2003 1880 Elizabeth F 1939 1880 Minnie F 1746 1880 Margaret F 1578 1880 Ida F 1472 1880 Alice F 1414 1880 Bertha F 1320 1880 Sarah F 1288 1880
14. 1列目を出力¶
ファイルの先頭10行に対して、各行の1列目だけを抜き出して表示せよ。確認にはcutコマンドなどを用いよ。
with open("../data/popular-names.txt", "r") as f:
lines = f.readlines()[:10]
for l in lines:
print(l.split(" ")[0])
Mary Anna Emma Elizabeth Minnie Margaret Ida Alice Bertha Sarah
!head -10 ../data/popular-names.txt | cut -f -1
Mary Anna Emma Elizabeth Minnie Margaret Ida Alice Bertha Sarah
15. ファイルをN分割する¶
ファイルを行単位でN分割し、別のファイルに格納せよ。例えば、N=10としてファイルを10分割せよ。同様の処理をsplitコマンドで実現せよ。
def split_to_n(path: str, n: int):
with open(path, "r") as f:
lines = f.readlines()
each = []
per = (len(lines) + 1) // n
for i in range(0, n):
each.append(lines[i:i+per])
for i, e in enumerate(each):
with open(f"../junk/{i}.txt", "w") as f:
f.writelines(e)
split_to_n("../data/popular-names.txt", 10)
!tldr split
warning: 1 page(s) found for other platforms: 1. common (tldr --platform common split) split Split a file into pieces. More information: https://keith.github.io/xcode-man-pages/split.1.html. Split a file, each split having 10 lines (except the last split): split -l 10 path/to/file Split a file by a regex. The matching line will be the first line of the next output file: split -p cat|^[dh]og path/to/file Split a file with 512 bytes in each split (except the last split; use 512k for kilobytes and 512m for megabytes): split -b 512 path/to/file Split a file into 5 files. File is split such that each split has same size (except the last split): split -n 5 path/to/file
%%bash
N=10
lcount=$(wc -l < ../data/popular-names.txt)
per=$(( (lcount + N - 1) / N )) # 向上取整,保证正好 N 份
split -l "$per" ../data/popular-names.txt ../junk/
16. ランダムに各行を並び替える¶
ファイルを行単位でランダムに並び替えよ(注意: 各行の内容は変更せずに並び替えよ)。同様の処理をshufコマンドで実現せよ。
17. 1列目の文字列の異なり¶
1列目の文字列の異なり(文字列の種類)を求めよ。確認にはcut, sort, uniqコマンドを用いよ。
18. 各行の1列目の文字列の出現頻度を求め、出現頻度の高い順に並べる¶
1列目の文字列の出現頻度を求め、出現頻度と名前を出現頻度の多い順に並べて表示せよ。確認にはcut, uniq, sortコマンドを用いよ。
19. 3列目の数値の降順に各行を並び替える¶
3列目の数値の逆順でファイルの各行を整列せよ(注意: 各行の内容は変更せずに並び替えよ)。同様の処理をsortコマンドで実現せよ。