bash マトリクス変換shell
#!/bin/bash
#(1)カンマ変換シェル
#csvファイルを取得
csvfile=$1
ymd=$(date '+%Y%m%d%H%M%S')
lineprime=1
cp ${csvfile} ${csvfile}_bk #ファイル全体の行数を取得
fileline=$(grep -c "." ${csvfile}_bk)
#整形ファイル
outputfile=${ymd}_shaping.txt
#縦の論理
while read line; do
#現在行を取得
currentline=$lineprime
#現在行がファイルの全体行数よりも大きい場合はbreakで抜ける 。
#if [[ $currentline -gt $fileline ]]; then
# break
#fi
#前行を取得
#beforeline =$(expr $currentline - 1)
#前行のカンマ数 (最大数)を取得
#beforelinekanma =$(sed -n ''${beforeline}p'' ${csvfile}_bk | awk -F ',' '{print NF}')
#現在行のカンマ数 (最大数)を取得
currentlinekanma=$(sed -n ''${currentline}p'' ${csvfile}_bk | awk -F ',' '{print NF}')
#########################
# 前行カンマ整形処理 start
tmpprime=0
for prime in $(seq 1 $currentlinekanma); do
#前行の配列を取得
currentarray_index=$(sed -n ''${currentline}p'' ${csvfile}_bk | awk -F [,] '{print $'$prime'}')
if [[ $(echo $currentarray_index | grep "." | wc -l) -eq 1 ]]; then
tmpprime=$prime
fi
done
#最末尾の値以降のnull部分以外のみをcsvファイルに残す
tmpprime2=$(sed -n ''${currentline}p'' ${csvfile}_bk | cut -d ',' -f -${tmpprime})
sed -i ''${currentline}''d ${csvfile}_bk
#最終行だけ挿入できない問題を解消するために分岐
if [[ $currentline -eq $fileline ]]; then
sed -i '$a '${tmpprime2}'' ${csvfile}_bk
else
sed -i ''${currentline}'i '${tmpprime2}'' ${csvfile}_bk
fi
# カンマ整形処理 finish
#########################
lineprime=$((++lineprime))
done <${csvfile}_bk
#初期化
lineprime=1
while read line; do
lineprime=$((++lineprime))
#現在行を取得
currentline=$lineprime
#現在行がファイルの全体行数よりも大きい場合はbreakで抜ける 。
if [[ $currentline -gt $fileline ]]; then
break
fi
#前行を取得
beforeline=$(expr $currentline - 1)
#現在行のカンマ数 (最大数)を取得
currentlinekanma=$(sed -n ''${currentline}p'' ${csvfile}_bk | awk -F ',' '{print NF}')
#現在行のカンマ数 (最大数)の値取得
currentlinekanmaprime=$(sed -n ''${currentline}p'' ${csvfile}_bk | awk -F [,] '{print $'$currentlinekanma'}')
#前行のカンマ数 (最大数)を取得
beforelinekanma=$(sed -n ''${beforeline}p'' ${csvfile}_bk | awk -F ',' '{print NF}')
#前行のカンマ数 (最大数)の値取得
beforelinekanmaprime=$(sed -n ''${beforeline}p'' ${csvfile}_bk | awk -F [,] '{print $'$beforelinekanma'}')
#現在行のカンマ数 (最大数)の値取得が1の場合は、何もしない。
if [[ $currentlinekanma == 1 ]]; then
continue
fi
currentarray=()
#カンマ数が1以下の場合は現在の値だけを出力 。カンマ数が1以上であれば実施する。
if [[ $beforelinekanma -ge 1 ]]; then
#前行の配列を取得
beforearray=$(sed -n ''${beforeline}p'' ${csvfile}_bk | awk -F [,] '{print $0}' | sed 's/,/"" /g')
#コピーされた前行配列を 、現在行の(最大数-1)分だけコピーする。
count=0
for t in ${beforearray[@]}; do
currentarray+=($t)
count=$((++count))
#配列の末尾に現在行の現在行の最大数値を付与する
if [[ ${count} -eq $(expr ${currentlinekanma} - 1) ]]; then
currentarray+=($currentlinekanmaprime)
break
fi
done
else
currentarray+=($currentlinekanmaprime)
fi
#現在行を出力する 。
printnum=$(echo ${currentarray[*]} | sed 's/""//g' | sed 's/ /,/g')
sed -i ''${currentline}''d ${csvfile}_bk
#現在行がファイルの全体行数よりも大きい場合はbreakで抜ける 。
if [[ $currentline -eq $fileline ]]; then
sed -i '$a '${printnum}'' ${csvfile}_bk
else
sed -i ''${currentline}'i '${printnum}'' ${csvfile}_bk
fi
done <${csvfile}_bk
#退避ファイルを元ファイルに戻す #mv ${csvfile}_bk ${outputfile}
cat ${csvfile}_bk
[root@localhost ~]# shfmt a.sh > b.sh
[root@localhost ~]# mv b.sh substring_hierarchy_csv.sh
[root@localhost ~]# cat substring_hierarchy_csv.sh
#!/bin/bash
#csvファイルを取得
csvfile=$1
ymd=$(date '+%Y%m%d%H%M%S')
lineprime=1
cp ${csvfile} ${csvfile}_bk #ファイル全体の行数を取得
fileline=$(grep -c "." ${csvfile}_bk)
#整形ファイル
outputfile=${ymd}_shaping.txt
#縦の論理
while read line; do
#現在行を取得
currentline=$lineprime
#現在行がファイルの全体行数よりも大きい場合はbreakで抜ける 。
#if [[ $currentline -gt $fileline ]]; then
# break
#fi
#前行を取得
#beforeline =$(expr $currentline - 1)
#前行のカンマ数 (最大数)を取得
#beforelinekanma =$(sed -n ''${beforeline}p'' ${csvfile}_bk | awk -F ',' '{print NF}')
#現在行のカンマ数 (最大数)を取得
currentlinekanma=$(sed -n ''${currentline}p'' ${csvfile}_bk | awk -F ',' '{print NF}')
#########################
# 前行カンマ整形処理 start
tmpprime=0
for prime in $(seq 1 $currentlinekanma); do
#前行の配列を取得
currentarray_index=$(sed -n ''${currentline}p'' ${csvfile}_bk | awk -F [,] '{print $'$prime'}')
if [[ $(echo $currentarray_index | grep "." | wc -l) -eq 1 ]]; then
tmpprime=$prime
fi
done
#最末尾の値以降のnull部分以外のみをcsvファイルに残す
tmpprime2=$(sed -n ''${currentline}p'' ${csvfile}_bk | cut -d ',' -f -${tmpprime})
sed -i ''${currentline}''d ${csvfile}_bk
#最終行だけ挿入できない問題を解消するために分岐
if [[ $currentline -eq $fileline ]]; then
sed -i '$a '${tmpprime2}'' ${csvfile}_bk
else
sed -i ''${currentline}'i '${tmpprime2}'' ${csvfile}_bk
fi
# カンマ整形処理 finish
#########################
lineprime=$((++lineprime))
done <${csvfile}_bk
#実行確認
$ cat test.txt
1.java
,method_1_1
,method_1_2
2.java
,method_2_1
,method_2_2
3.java
,method_3_1
,method_3_2
4.java
,method_4_1
,method_4_2
$ bash substring_hierarchy_csv.sh test.txt csv
1.java
1.java,method_1_1
1.java,method_1_2
2.java
2.java,method_2_1
2.java,method_2_2
3.java
3.java,method_3_1
3.java,method_3_2
4.java
4.java,method_4_1
4.java,method_4_2
#!/bin/bash
#(2)カンマ戻し変換シェル
while read line
do
#デリミタ数を数える 。
delimiter_num=$(echo ${line}|awk -F ',' '{print NF}')
#末尾のデータを取る
suffixdata=$(echo ${line}|awk '{print $NF}')
#デリミタ数が1の場合は末尾だけを出す
if [[ ${delimiter_num} = 1 ]]; then
echo ${suffixdata}
#デリミタ数が2以上 (デリミタ数 - 1の数「,」 + 末尾データを出力する)
else
suffixdata=$(expr ${delimiter_num} - 1)
cat <(seq 1 ${suffixdata}|sed -E "s/[0-9]+/,/g"|tr "\n" " "|sed -E "s/ | $//g") <(echo ${line}|awk -F [,] '{print $NF}')
fi
done < ${1}
#確認
$ cat hoge
1.java
1.java,method_1_1
1.java,method_1_2
2.java
2.java,method_2_1
2.java,method_2_2
3.java
3.java,method_3_1
3.java,method_3_2
4.java
4.java,method_4_1
4.java,method_4_2
#実行をしてみる
$ bash substring_hierarchy_modoshi_csv.sh hoge
1.java
,method_1_1
,method_1_2
2.java
,method_2_1
,method_2_2
3.java
,method_3_1
,method_3_2
4.java
,method_4_1
,method_4_2
この記事が気に入ったらサポートをしてみませんか?