私はLinuxにとって比較的初心者なので、助けてくれて本当にありがとう。を使用していますが、grep
抽出されたすべての値(どの列に関係なく)の平均と、各ファイルから抽出された値(n)の数(各列に入力)も必要です。
注文する:
grep -o "201[1-4].[0-9][ -9]" file1.txt file2.txt file3.txt \ | awk -F: '
{
if (!s[$1]){ s[$1]=$2 }
else { s[$1]=s[$1]","$2 }
}
END {
for (f in s){ print f","s[f] }
}' | csvtool transpose -u " " - | column -nt
現在の出力:
file1.txt file3.txt file2.txt
2013.17 2012.69 2013.54
2012.6 2013.44 2013.9
2013.12 2012.64 2013.66
2012.76 2013.11 2013.44
2013.75 2012.6 2013.89
2013.08 2012.41 2013.62
2012.41 2013.41
2013.2
常に3つの列がありますが、行数は予測できません。
例:
file1.txt file3.txt file2.txt
1 2 3
2 1 1
2
n=2 n=2 n=3
Average: 1.714
私が使用するものの例:
ファイル1:
2896.79 2897.65 2898.82 2012.69 2013.44 2897.4 2896.79 2012.64 2896.71 2217.4 2013.11 2012.6 2012.41 2012.41 2013.2 2897.12 2896.61 2896.35 2896.85 2896.26 2896.72
2913.91 2914.41 2914.27 2329.68 2329.71 2914.15 2914.32 2321.19 2914.02 2329.32 2896.49 2025.55 2328.84 2328.98 2329.1 2913.96 2913.48 2913.36 2913.97 2913.46 2913.71
2925.09 2925.58 2926.69 2401.39 2897.65 2925.77 2925.55 2328.96 2924.86 2897.19 2913.95 2029.61 2896.86 2896.93 2764.59 2925.18 2924.96 2924.68 2925.03 2924.18 2924.72
2933.54 2933.91 3196.19 2897.73 2914.79 3314.12 3016.04 2400.29 3015.62 2914.03 2925.09 2897.07 2913.69 2914.41 2897.38 2934.31 3058.51 3015.26 2934.32 2932.55 2933.38
2952.71 2953.49 3223.9 2914.91 2926.03 3321.3 3066.1 2896.71 3065.91 2925.14 2934.16 2914.04 2924.74 2925.54 2914.6 2952.92 3065.18 3065.74 2953.23 3072.91 2952.84
3016.02 3016.4 3249.51 2925.73 2932.82 3373.04 3073.91 2913.87 3073.65 2953.29 2952.94 2925.78 2952.15 2933.65 2925.67 3015.76 3073.21 3072.94 3065.81 3222.86 3015.45
3065.42 3059.27 3313.84 2953.72 2953.17 3444.15 3081.47 2925.02 3192.84 3015.73 3015.47 2953.12 3015.35 2953.29 2953.84 3073.71 3223.42 3080.34 3073.98 3312.09 3059.03
ファイル2:
2013.17 2012.6 2013.12 2036.82 2037.29 2036.53 2036.44 2032.6 2032.88 2012.76 2037.57 2037.26 2037.5 2042.89 2038.1 2013.75 2037.73 2038 2037.93 2033.5 2033.26 2013.08
2033.07 2033.03 2032.99 2042.08 2042.15 2042.14 2041.82 2036.84 2036.88 2033.27 2042.66 2042.65 2042.61 2461.68 2042.94 2037.45 2042.99 2042.96 2043.04 2037.29 2037.32 2033.44
2037.25 2037.27 2037.26 2080.15 2080.48 2080.35 2079.99 2042.18 2042.22 2037.31 2461.16 2080.81 2080.72 2465.94 2461.39 2043 2081.13 2081.08 2081.26 2042.62 2042.63 2037.55
2042.56 2042.49 2042.41 2464.77 2465.3 2465.08 2460.36 2053.03 2465.1 2042.58 2465.84 2461.76 2460.66 2473.93 2466.23 2461.58 2461.48 2461.6 2466.06 2053.48 2053.35 2042.68
2053.26 2053.42 2053.79 2480.18 2473.43 2472.84 2464.91 2080.37 2480.47 2058.27 2473.22 2465.78 2465.78 2482.02 2474.04 2466.07 2466.05 2466.01 2474.01 2080.88 2080.75 2053.24
2076.01 2059.33 2058.08 2500.19 2481.17 2480.7 2472.76 2460.1 2529.24 2076.3 2481.38 2473.76 2473.51 2501.38 2482.1 2473.97 2474.02 2473.99 2482.05 2276.73 2276.52 2058.42
2080.83 2075.97 2075.97 2529.14 2529.55 2529.28 2481.04 2465.12 2537.59 2080.44 2489.75 2481.63 2481.37 2525.17 2490.26 2482.1 2481.98 2481.96 2501.93 2465.52 2465.58 2076.22
2250.64 2080.54 2080.49 2537.07 2536.95 2537.65 2487.59 2473 2619.65 2276.27 2496.5 2500.38 2489.45 2530.2 2502.23 2525.03 2490.46 2501.06 2530.44 2500.93 2481.26 2080.85
2276.67 2118.71 2275.92 2635.42 2547.03 2544.73 2503.45 2480.94 2636.12 2465.35 2500.25 2524.95 2524.14 2538.07 2524.69 2530.47 2530.45 2524.9 2538.6 2529.88 2500.92 2276.34
ファイル3:
2207.2 2003.43 6628.01 2013.54 2013.9 2914.93 2003.72 3315.09 2013.66 2013.44 2147.76 2147.67 2207.45 2147.93 2013.89 2013.62 2008.56 2914.99 6632.04
2252.13 2036.51 2147.79 2036.93 2926.08 2013.41 5833.85 2037.51 2037.41 2206.79 2207.16 2898.47 2207.22 2037.11 2147.77 2037.9 3060
2639.52 2120.66 2206.81 2147.77 3016.02 2036.57 6630.91 2147.94 2147.93 2914.59 2914.66 2915.5 2898.31 2207.46 2206.73 2147.96 3225.13
2829.69 2147.96 2329.47 2207.1 3059.21 2147.81 2207.22 2207.15 3015.96 3058.98 2926.66 2915.11 2898.69 2329.31 2166.65 3314.22
2914.74 2206.87 2897.84 2252.53 3225 2329.91 2329.35 2329.69 3031.21 3224.88 3059.82 2926.17 2915.3 2897.89 2207.42 5833.23
3015.61 2252.38 2914.72 2329.72 3265.74 2897.86 2897.85 2897.81 3058.98 3265.62 3225.63 3059.46 2926.66 2914.67 2253.44 6034.36
3030.72 2329.24 2925.98 2897.89 3305.35 2914.99 2915 2914.72 3077.57 3305.36 3266.57 3225.4 3016.03 2925.65 2330.06 6121.01
答え1
ワンステップで実際の問題を解決してください。
$ grep -o '201[1-4].[0-9]\+' file1.txt file2.txt file3.txt \
| datamash --sort -t: -g1 count 2 mean 2
file1.txt:8:2012.8125
file2.txt:6:2013.08
file3.txt:7:2013.6371428571
grep
ファイルから値を取得し、datamash
ファイルごとに項目数を計算し、平均を計算します。
各ファイルには1行しかありません。filename:n:average
簡単ですよね?
すべてのファイルの平均を取得するには、グループ化を削除します。
grep -o '201[1-4].[0-9]\+' file1.txt file2.txt file3.txt \
| datamash --sort -t: mean 2
2013.1638095238
素晴らしいテーブル出力を印刷する必要がある場合は、次を試してください。
$ cat mktable.sh
#!/bin/bash
myfiles="$@"
trap "rm ${myfiles//txt/txt.tempfile}" EXIT SIGTERM SIGINT
declare -A count
for f in $myfiles ; do
# write the tempfile AND get the linecount simultaneously
count[$f]="$(grep -o '201[1-4].[0-9]\+' "$f" | tee ${f}.tempfile | wc -l)"
sed -i "1i $f" ${f}.tempfile # write header
sed -i "2i ---------" ${f}.tempfile # write header
done
( paste ${myfiles//txt/txt.tempfile} ;
for item in $myfiles ; do echo -n '--------- '; done; echo
for item in $myfiles ; do echo -n "n=${count[$item]} " ; done ; echo ;
for item in $myfiles ; do echo -n '--------- '; done; echo
)\
| column -nt
echo "Average: $(grep -o '201[1-4].[0-9]\+' $myfiles | datamash -s -t: mean 2)"
$ ./mktable.sh file*.txt
file1.txt file2.txt file3.txt
--------- --------- ---------
2012.69 2013.17 2013.54
2013.44 2012.6 2013.9
2012.64 2013.12 2013.66
2013.11 2012.76 2013.44
2012.6 2013.75 2013.89
2012.41 2013.08 2013.62
2012.41 2013.41
2013.2
--------- --------- ---------
n=8 n=6 n=7
--------- --------- ---------
Average: 2013.1638095238
答え2
AWKを使用してすべてを処理します。
#!/usr/bin/gawk -f
BEGIN {
RS = " +|\t+|\n"
OFS = "\t"
}
$1 >= 2011 && $1 < 2015 {
counts[FILENAME]++
allcounts++
allsum += $1
values[FILENAME][length(values[FILENAME])] = $1
}
END {
for (file in counts) {
printf "%s%s", file, OFS
if (counts[file] > maxlength) {
maxlength = counts[file]
}
}
printf "\n"
for (i = 0; i < maxlength; i++) {
for (file in counts) {
if (i < counts[file]) {
printf "%.2f", values[file][i]
}
printf "%s", OFS
}
printf "\n"
}
printf "\n"
for (file in counts) {
printf "n=%d%s", counts[file], OFS
}
printf "\n"
printf "Average: %f\n", allsum / allcounts
}
ファイル(たとえば546830
)に保存して実行可能にした後(chmod 755 546830
)、次のように実行します。
./546830 file1.txt file2.txt file3.txt
以下を使用して列を並べ替えることができますcolumn
。
./546830 file1.txt file2.txt file3.txt | column -t
あなたの質問に与えられた例を使用すると、
file1.txt file3.txt file2.txt
2012.69 2013.54 2013.17
2013.44 2013.90 2012.60
2012.64 2013.66 2013.12
2013.11 2013.44 2012.76
2012.60 2013.89 2013.75
2012.41 2013.62 2013.08
2012.41 2013.41
2013.20
n=8 n=7 n=6
Average: 2013.163810
出力のファイル順序が入力の順序と必ずしも一致する必要はありませんが、値が混乱するわけではありません。順序が重要な場合は、スクリプトを変更してそれを維持できます。
どのように機能するかは、各ファイルを空白と改行のレコードに分割し、基準(2011〜2015を除く)を満たす各レコードをファイル名とvalues
数で索引付けされた配列に保存することです。値もallsum
アキュムレータに追加され、ファイルあたりの数は配列に保存され、集計counts
数はallcounts
アキュムレータに保存されます。