Edited at

bashでIFSを使わずにsplitする方法


はじめに

こんな方法があるなんて知らなかった。

IFSなんていらなかったんだ!

ここに載っていたのを模倣しただけです。

でも日本語の記事が見当たらなかったので書きました。


環境


  • OS: macOS Sierra 10.12.4

  • bash: GNU bash, version 3.2.57


やりたいこと

文字列を指定したデリミタで分割して配列に格納したい。

いわゆるsplitです。


まずは結論から

例えばパスからディレクトリの配列を得るにはこうなる。

split(というか置換してるだけ)の処理は一行。便利!


split-sub.sh

#!/bin/bash

path=$1;
declare -a a_dirs=();
a_dirs=${path//\// };

for dir in ${a_dirs[@]};
do
echo $dir;
done

exit 0;



実行結果

$ ./split-sub.sh $(pwd)

Users
tommarute
script
split_test


今までの方法

よくあるIFSを使ったやり方。


split-ifs.sh

#!/bin/bash

function split() {
local -a _dirs=();
path=$1;
c_ifs=$IFS;
IFS=$2;
_dirs=$(echo $path);
IFS=$c_ifs;
echo $_dirs;
}

main() {
declare -a a_dirs=();
a_dirs=($(split $1 '/'));

for dir in ${a_dirs[@]};
do
echo $dir;
done
exit 0;
}

main $@;



実行結果

$ ./split-ifs.sh $(pwd)

Users
tommarute
script
split_test


おまけ

今回書いた方法は、デリミタを空白に置換して配列に変換しているわけで、であればtrでもできるんじゃ。。

と思ってやってみたらできました。

気づかなかった。

#!/bin/bash

path=$1;
declare -a a_dirs=();
a_dirs=$(echo $path | tr '/' ' ');

for dir in ${a_dirs[@]};
do
echo $dir;
done

exit 0;


実行結果

$ ./split-tr.sh $(pwd)

Users
tommarute
script
split_test


おわりに

bashでIFSを使わずにsplitする方法について書きました。

今までIFS使って書いたコード全てリファクタリングしたい。

!!!ご注意!!!

この記事はあくまで私がIFSを使ったsplitより簡単だと感じた手法について書いたものであり、決してIFSを否定するものではありません。