【GAS】多分、恐らく、全く無意味な関数を作ってしまった(INDIRECT関数凄い)
GoogleスプレッドシートにはINDIRECTという関数がある。
これはとても便利な関数と何処かで読んだ事がある。
改めて利用例を色々見ると、関数を書き換えなくても動的に関数の動作を変えることが出来る関数というのが正しい理解であろうか。
この関数は便利そうである。
よく見かける利用例はこんなので、行数が不確定なデータの合計を取る必要がある場合どうするのかというもの。
=SUM(A1:A16)
と、このように指定した場合、行数が変わったら関数を書き換えなければならない。
ここで、行数を調べるために=COUNTA(A:A)として行数を調べる。
で、=SUM("A1:A"&COUNTA(A:A))としたいがエラーになる。
これを解決するのがINDIRECT関数という説明で以下のようにする。
=SUM(INDIRECT( "A1:A"&COUNTA(A:A)))
これで行数が増えても減ってもA列をカウントした数までSUMの対象になる。
INDIRECT関数で文字や数値を関数に渡すことで、色々と動的に関数の挙動が変えられるわけだ。
でも、COUNTAだと間に空白行があったら、空白はカウントしないから範囲がずれてしまう。
事例には続きがあり、もっと複雑な関数の組み合わせで空白行があっても最終行を対応する事が出来る事例が掲載されていた。
だが、その事例を見た私は、こんな複雑で見づらい関数の組み合わせを使いたくないと思った。(MAX関数とMATCH関数を用いるものであったがここでは割愛する)
であるから、シンプルに最終行を取得するユーザー関数を作ってしまったのである。
「作ってしまった」
だって多分恐らく全く無意味だから・・・。
とりあえず、作ってしまった無意味な関数を使う場合こうなる
=TOMM(A:A)
これで最終行が数値で取得できる。
空白行があっても問題はない
なので、空白行があっても対応できる範囲が可変なSUM関数はこんな感じで使える。
=SUM(INDIRECT( "A1:A"&TOMM(A:A)))
シンプル!、MATCH関数を組み合わせるような利用例と比べたらかなりシンプル!
と喜びたいのだけど、でもねぇ・・・。
元々の利用例自体が、なんか無理やりINDIRECT関数を使っているなぁと思う。
だって、=SUM(A:A)これだけで目的は達成できてしまうのであるから。行が増えたって問題なくSUM関数一つで済んでしまう。
それに、GoogleスプレッドシートのINDIRECT関数の使用例としてもどうかと思う。
というのも、GoogleスプレッドシートのINDIRECT関数は複数範囲を参照し複数範囲に展開出来てしまうのである。
複数範囲を取得し展開出来ると何が凄いのか? 単体で使うとわかりづらいがこれを関数の入れ子にすると劇的に便利なことがわかる。
=SUM(INDIRECT("A:A"))
まぁSUM関数だけで済んでしまうこの事例では、あまり有り難みが感じられないが、INDIRECT関数の時点で範囲を展開出来るのでINDIRECT関数にCOUNTAで動的に範囲を変動させる必要なんて無いのである。
ちょっと気になってINDIRECT関数の挙動をLibreOffice Calcで確認した。
やはり複数セルに展開されない。
んー? しかし、複数セルには展開されないけどSUMで入れ子にすると合計は出た。
という事はINDIRECT関数のGoogleスプレッドシートの違いは複数セルに展開できる点のみとうい事であろうか?
ヘルプを参照するとこのようになっている。
複数範囲を指定できることも記していなければ、複数セルに展開出来ることも記していない。
サンプルも同様。
これじゃあ、従来の表計算ソフトと同じような事例がいろんなところに掲載されてもしょうがない。
まとめ
GoogleスプレッドシートのINDIRECT関数は従来の表計算ソフトと同様に関数を書き換えなくても範囲を動的に変更させることが出来る。
そして、従来の表計算ソフトと異なり、複数範囲を複数セルに展開出来る。
つまりは同じスプレッドシート内の異なるシートであればIMPORTRANGE関数のように範囲を取得できるということである。
これは集計シートとデータシートを明確に分けてデータベースのように扱うことが可能であることを意味している。INDIRECTを入れ子にしてQUERY関数を用いれば様々な事が出来るであろう。
さて、最後に多分恐らく全く無意味な自作関数のソースを掲載する。
掲載したSampleのスプレッドシートは以下のリンクから確認出来る。
TOMM ←スプレッドシートにリンク
FreeSpaceというシートは自由に編集できるようになっているので興味があるならTOMM関数とINDIRECT関数の連携を試したり出来る。
ちなみにTOMMはTabun Osoraku Mattaku Muimiからきている。
発音はトム、但し、母音の「ぅ」が出ないように「む」と発音した瞬間に口を閉じて欲しい!
これはとても便利な関数と何処かで読んだ事がある。
改めて利用例を色々見ると、関数を書き換えなくても動的に関数の動作を変えることが出来る関数というのが正しい理解であろうか。
この関数は便利そうである。
よく見かける利用例はこんなので、行数が不確定なデータの合計を取る必要がある場合どうするのかというもの。
=SUM(A1:A16)
と、このように指定した場合、行数が変わったら関数を書き換えなければならない。
ここで、行数を調べるために=COUNTA(A:A)として行数を調べる。
で、=SUM("A1:A"&COUNTA(A:A))としたいがエラーになる。
これを解決するのがINDIRECT関数という説明で以下のようにする。
=SUM(INDIRECT( "A1:A"&COUNTA(A:A)))
COUNTAでの増減対応例 |
INDIRECT関数で文字や数値を関数に渡すことで、色々と動的に関数の挙動が変えられるわけだ。
でも、COUNTAだと間に空白行があったら、空白はカウントしないから範囲がずれてしまう。
事例には続きがあり、もっと複雑な関数の組み合わせで空白行があっても最終行を対応する事が出来る事例が掲載されていた。
だが、その事例を見た私は、こんな複雑で見づらい関数の組み合わせを使いたくないと思った。(MAX関数とMATCH関数を用いるものであったがここでは割愛する)
であるから、シンプルに最終行を取得するユーザー関数を作ってしまったのである。
「作ってしまった」
だって多分恐らく全く無意味だから・・・。
とりあえず、作ってしまった無意味な関数を使う場合こうなる
=TOMM(A:A)
これで最終行が数値で取得できる。
空白行があっても問題はない
なので、空白行があっても対応できる範囲が可変なSUM関数はこんな感じで使える。
=SUM(INDIRECT( "A1:A"&TOMM(A:A)))
シンプル!、MATCH関数を組み合わせるような利用例と比べたらかなりシンプル!
と喜びたいのだけど、でもねぇ・・・。
元々の利用例自体が、なんか無理やりINDIRECT関数を使っているなぁと思う。
だって、=SUM(A:A)これだけで目的は達成できてしまうのであるから。行が増えたって問題なくSUM関数一つで済んでしまう。
SUMだけで行数の増減には対応できる |
それに、GoogleスプレッドシートのINDIRECT関数の使用例としてもどうかと思う。
というのも、GoogleスプレッドシートのINDIRECT関数は複数範囲を参照し複数範囲に展開出来てしまうのである。
GoogleスプレッドシートのINDIRECT関数は範囲を展開する |
=SUM(INDIRECT("A:A"))
まぁSUM関数だけで済んでしまうこの事例では、あまり有り難みが感じられないが、INDIRECT関数の時点で範囲を展開出来るのでINDIRECT関数にCOUNTAで動的に範囲を変動させる必要なんて無いのである。
ちょっと気になってINDIRECT関数の挙動をLibreOffice Calcで確認した。
LibreOffice Calc INDIRECT |
んー? しかし、複数セルには展開されないけどSUMで入れ子にすると合計は出た。
という事はINDIRECT関数のGoogleスプレッドシートの違いは複数セルに展開できる点のみとうい事であろうか?
ヘルプを参照するとこのようになっている。
複数範囲を指定できることも記していなければ、複数セルに展開出来ることも記していない。
サンプルも同様。
これじゃあ、従来の表計算ソフトと同じような事例がいろんなところに掲載されてもしょうがない。
まとめ
GoogleスプレッドシートのINDIRECT関数は従来の表計算ソフトと同様に関数を書き換えなくても範囲を動的に変更させることが出来る。
そして、従来の表計算ソフトと異なり、複数範囲を複数セルに展開出来る。
つまりは同じスプレッドシート内の異なるシートであればIMPORTRANGE関数のように範囲を取得できるということである。
これは集計シートとデータシートを明確に分けてデータベースのように扱うことが可能であることを意味している。INDIRECTを入れ子にしてQUERY関数を用いれば様々な事が出来るであろう。
さて、最後に多分恐らく全く無意味な自作関数のソースを掲載する。
function TOMM(selectColumn) {この使い道が無い関数は当然誰でも自由に使って良いので何か役に立つ使いみちがあるならコピーして使っていただきたい。
var LastRow = selectColumn.length; //配列の数を取得
var i = LastRow;
for (i == 0;i--;){
if(selectColumn[i][0] == ""){
selectColumn.pop();
}else{
break;
}
}
LastRow = selectColumn.length; //空欄削除後の配列の数を取得
return LastRow;
}
掲載したSampleのスプレッドシートは以下のリンクから確認出来る。
TOMM ←スプレッドシートにリンク
FreeSpaceというシートは自由に編集できるようになっているので興味があるならTOMM関数とINDIRECT関数の連携を試したり出来る。
ちなみにTOMMはTabun Osoraku Mattaku Muimiからきている。
発音はトム、但し、母音の「ぅ」が出ないように「む」と発音した瞬間に口を閉じて欲しい!
コメント
コメントを投稿