bashの配列と連想配列
もう、酷いとしか言いようが無い。
- たぶん、declare宣言でしか連想配列を指定できない。リテラル風の記法はない(たぶん)。
- 配列と連想配列で、a[i] と a[i] の解釈が異なる。
- 配列と連想配列で、a[1] と a[1] が${}内で使えるが、内部的解釈はたぶん異なる。
- 配列と連想配列で、a[-1] と a[-1] が${}内で使えるが、解釈は異なる。
- 配列と連想配列で、#a[@] が${}内で使えるが、これの解釈は同じと言える。だが、配列の場合は極めて誤りやすい。
- 配列と連想配列で、名前のみを${}内で使うと、これの解釈は同じと言える。だが、誤解しやすい。名前のみはキー'0'でアクセする。
- 配列の-1は、そのときのキーの最大値を意味する。空配列では、-1キーは未定義。
- 配列のキーの最大値(最後のキー)を簡単に知る方法はないと思う。
- 配列のキーの最大値をNとして、-1 から -(N + 1) = -N - 1 = -1 - N までの負のキーが使える。この範囲にないキーは違法となる。
- 共通に使えるコード: for k in "${!ass[@]}"; do echo $k; done
- 共通に使えるコード: for k in "${!ass[@]}"; do echo $k ${ass[$k]}; done
"${!ass[@]}" でキーのワードリスト、"${ass[@]}" で値のワードリストが作られる。クォートしないと意味が変わる。
元が配列のようなデータ並び(複合データ)である場合、次のようにしてワードリスト(フィールドを持つレコード)を作る。
- クォートされてない場合:
- データ並びをそのまま標準のフィールド区切り記号(IFS文字のひとつ)を挟んでジョインする。
- IFSを使ってワード分割する。それぞれのワードからワードリストを作る。
- クォートされている場合:
- データ並びをクォーティングしてから標準のフィールド区切り記号(IFS文字のひとつ)を挟んでジョインする。
- IFSを使ってワード分割する。このとき、ワード分割はクォーティングを理解する。それぞれのワードからワードリストを作る。
データ並びの項目をクォーティングするときのクォートは実際の文字「"」というよりは、何か内部的な仕掛けと思ったほうがよい。
ワードリストの利用場面は:
- コマンドの引数リスト
- forの繰り返し項目リスト
- 配列初期化の配列項目リスト