Excel スピル(動的配列数式) とバージョン間の互換性
これは,Spreadsheets/Excel Advent Calendar 2019の記事です.
いよいよExcelにスピルがやってきました!
スピルとは
1年ちょっと前にOffice 365 Insiderの「スピル」という機能について少し話題になりました. 「スピル (spill)」というのは,配列を返す数式の結果が, 隣接するセル範囲に「しみ出す (spillする)」という新機能です.
たとえば,下記のように数式を入力すると,
このように下のセルにも値が表示されます*1. 値が「しみ出した」範囲が青色の枠で囲われています.
このスピルする配列を返す数式は,新たに「動的配列数式 (dynamic array formula)」と呼ばれています.
スピル先のセルを選択すると,数式バーに数式が灰色で表示されます.これをゴーストと呼びます.
ゴーストが表示されたセルの数式を編集しようとしても,何も出てきません.
数式を編集するには,スピル元のセル(ここではB1セル)を選択します.
スピル先のセルでは,数式は実在しませんが,値は実在します.
なので,下記のように別のセル(C3)から値を参照したり,色など書式を付けたりできます.
配列数式との違いは?
今まで存在した「配列数式(CSE; Ctrl+Shift+Enterで確定する数式)」では,値を表示する各セルに数式を入れる必要がありましたが,動的配列数式の結果がスピルすることによって,1つのセルだけに数式を入れれば済みます.
配列数式も引き続き使用できますが,Microsoftとしてはあくまで旧バージョンとの互換性のために残しただけで,今後は代わりにスピル機能を使うべきということです.
いつから使える?
現在ではExcel Onlineやスマホ版Excel (iPhone, Android) でもスピル機能が使えるようになっています.
そして,デスクトップ版Excel 365でも,2019年12月3日のアップデートでいよいよ使えるようになったようです(参考: 「Excel」に6つの関数と新しい配列数式が導入~「Office 365」の2019年11月更新 - 窓の杜)
過去のバージョンのExcelとの互換性は?
スピル機能に関してMicrosoft曰く,「動的配列数式をサポートするためにExcelの数式言語に大幅なアップデート」を行ったそうですが,互換性はどうなのでしょうか?
以下,便宜的にスピル機能実装前のExcelを「旧Excel」,実装後のExcelを「新Excel」と表記します.
旧Excel ➡ 新Excel の場合
基本的には旧バージョンのExcelの数式は,新バージョンのExcelでもそのまま動きます.
スピル機能と競合しそうな旧Excelの機能として,「(暗黙的な)共通部分の参照」というものがあります.
これは,旧Excelでセル範囲(A1:A3
など)を返す数式の結果は,「同じ行」または「同じ列」の値のみが選択されて返されるという機能です.下の画像を見るとわかると思います.
選択されているセルに=A1:A3
や=A1:C1
といった範囲を返す式が入っていますが,同じ行,同じ列の値のみが表示されていますね.
この数式をそのまま新Excelで開くと,結果がスピルするために同じ数式なのに違う結果になってしまいそうです.
これを解決するために導入されたのが,暗黙的なインターセクション演算子 (Implicit intersection operator) @
です*2.
@セル範囲
のように書くことで,新Excelでも,(スピルするのではなく)共通部分の参照を行います.
そして,旧Excelでセル範囲を返す数式は,新Excelで開くと自動的に先頭に@
が挿入されます.
これによって,新Excelでも同じ計算結果になります. (ただ,勝手に@が付くので知らない人は混乱するかもませんね.)
逆に,新Excelの数式であえて@
をセル範囲の先頭に付けてスピルしないようにすると,旧Excelではその数式は@
が除かれて表示されます.
なお,旧Excelの配列数式は,新Excelでもそのままです.
VBAは?
多くの場合はVBAの動作にも影響はしないと考えられます. (このあたりは検証しておらず,ネット上の情報を参考にしたものです.)
ただし,RangeオブジェクトのValueプロパティで数式を設定すると,新Excelの数式として解釈されるようになるため,数式の挙動が変わる可能性があります.
これを回避するには,Formulaプロパティで設定することで,新Excelでも引き続き旧Excelの数式として解釈されます.
まあ,Valueプロパティで共通部分の参照を利用した数式を設定する機会はそう多くないと思いますが... もしあった場合はエラー値や異なる値になる可能性はあります.
なお,新Excelにおいて,Formulaプロパティは旧Excelの形式で数式を返すし,数式を代入すると旧Excelのものとして解釈します. なので,数式の取得には影響しなさそうです.
逆に,新ExcelのVBAで新機能を使った数式を設定したい場合は,新たに追加されたFormula2プロパティ(またはValueプロパティ)を使います.
新Excel ➡ 旧Excelの場合
逆に,新バージョンのExcelでスピルを使った数式は,気をつけないと旧バージョンでエラーになることがあります.
旧Excelで問題無いパターン
新Excelで単純にスピルだけを使用した場合は,旧Excelでは配列数式として解釈されます.(参考)
例えばこんな感じでスピルさせた数式を新Excelで保存すると,
旧Excelではこのように表示されます.B1:B3セルが配列数式になっており,新Excelと同じ結果になります.
しかし旧Excelでエラーになる場合もあります.
旧Excelでエラーになるパターン
旧Excelで問題になるのは,例えばスピル範囲演算子#
を使っている場合です.
スピル範囲演算子#
とは,セル参照の後につけることで,「そのセルからスピルしている範囲」を表すという演算子です.
例えば,下記では,B1#
がB1:B3
と解釈されます(B1セルには,=A1:A3
という式が入っています).
スピルと組み合わせると大変便利ですが,旧Excelで開くと下記のようにANCHOARRAY
という関数になり,この関数は未定義なので,#NAME?
エラーになります.
なお,Excelの互換性チェック機能で,配列数式として保存される数式をチェックできるようです.(未検証)
また,スピル機能と共に導入された,FILTER, SORT, SORTBY, UNIQUE, SEQUENCE, RANDARRAY関数やその他新しい関数も旧Excelではエラーになります.
VBAの互換性
あとは,VBAでスピル特有の機能を使っている場合,旧Excelでは動かなくなります.
新Excelでは,Rangeオブジェクトに対して,スピルしている範囲を返すSpillingToRange
やスピルされているか否かを返すHasSpill
といった便利なプロパティが追加されています.
当然,それらは旧Excelでは存在しないので,VBAはエラーになります.
また,Rangeに指定するアドレスでスピル範囲演算子#
を使っていたり,Valueで新しい形式の数式を代入したりしていても,もちろん旧Excelではうまく動きません.
スピル機能を使ったVBAを書く際は,実行環境のExcelのバージョンをしっかりと確認する必要がありそうです.
まとめ
数式の互換性について下記にまとめます.
機能 | 旧Excel | 自動変換 | 新Excel | 解説 |
---|---|---|---|---|
単一範囲の参照 | =A1 | - | =A1 | 変わらない |
配列数式 | {=A1:A3} | - | {=A1:A3} | そのまま使える(ただし新Excelでは非推奨) |
スピル | {=A1:A3} | ⬅ | =A1:A3 | 旧Excelでは配列数式になる |
共通部分の参照 | =A1:A3 | ⬅/➡ | =@A1:A3 | 新Excelでは@ 演算子で共通部分を参照 |
スピル範囲演算子 | #NAME? | x | =B1# | 旧Excelではエラー |
新たな関数 | #NAME? | x | =SORT(A1:A3) | 旧Excelではエラー |
デスクトップ版Officeで使えるようになったら,互換性に注意しつつ使っていきたいです!
関連記事:
この記事が詳しいです.参考にしました: Office TANAKA - Excel VBA Tips[動的配列数式の操作]