Synthetic Data Generator タブ

Synthetic Data Generator タブは、列ごとに分布を宣言したデータ生成過程(DGP: data generating process)からデータセットを作ります。回帰・群構造・時系列・パネル・生存時間のデータを、外部ファイルなしで用意できます。生成に使った真のパラメータが分かっているため、分析手法の挙動の確認や操作の練習に使えます。

同じ定義からのデータ生成は、Agent API の datasets.generateSynthetic でも実行できます。spec の JSON 形式・オプション・エラーコードは Agent API を参照してください。

データの生成

メニューバーの Data > Generate Synthetic Data... を選ぶと、タブが開きます。

フォームでは Dataset name・Rows・Seed を入力し、Columns に列を並べて 1 列ずつ分布とパラメータを決めます。Add Column で列を増やし、行末のごみ箱ボタンで列を消します。Seed は −2,147,483,648 から 2,147,483,647 までの整数です。Rows は 10,000,000 以下の正の整数です。

Synthetic Data Generator のフォーム

Generate Preview は入力を検証し、データを生成して先頭 10 行を表示します。入力に誤りがあると、Generate Preview はエラーメッセージを表示し、それまでのプレビューを消します。

プレビューの確認と保存

Save as Dataset を押すまで、プロジェクトのデータセットは増えません。Generate Preview を何度やり直しても、既存のデータセットは変わりません。

プレビューと Save as Dataset ボタン

Save as Dataset を押すとデータセットができ、Data Table タブが開いて Synthetic Data Generator タブは閉じます。

既存のデータセットと同じ名前で保存しようとすると、名前の変更・連番の付与・置換を選ぶダイアログが開きます。置換は、置換先も Synthetic Data Generator タブで作ったデータセットの場合にだけ選べます。それ以外の場合、ダイアログは置換の選択肢を無効にして理由を表示します。

列と分布

各列は分布を 1 つ持ちます。分布のパラメータは式で指定します。式は他の列を参照できるため、列の間の依存関係で生成過程を表現します。式の書き方は 式の構文 を参照してください。

選べる分布は 8 種類で、パラメータ欄は分布ごとに変わります。各パラメータの意味と分布の形は 確率分布の基礎 で説明しています。

分布パラメータ列のデータ型
NormalMean、SDfloat64
UniformMin、Maxfloat64
Bernoulli (0/1)Pint64
CategoricalLevels、Weightsstring
PoissonLambdaint64
GammaShape、Scalefloat64
WeibullShape、Scalefloat64
DeterministicValuefloat641

Deterministic はノイズを持たず、式の値をそのまま列にします。線形予測子 の列や、他の列を変換した列を作るときに使います。

Categorical では、Levels にカンマ区切りで水準を並べ、Weights に水準ごとの重みを書きます。Weights を省くとすべての水準を同じ確率で選びます。Weights の各要素も式なので、行ごとに変わる重みを書けます。MIDAS は負の重みと、すべてが 0 になる重みを拒否します。

Gamma と Weibull は Shape と Scale でパラメータ化します。Gamma の平均は Shape × Scale、分散は Shape × Scale² です。Weibull の平均は Scale × Γ(1 + 1/Shape) です(Γ はガンマ関数)。

列のデータ型と測定尺度の対応は データ型と測定尺度 を参照してください。

式の値がパラメータの定義域を外れると、生成は失敗します。Normal の SD が 0 以下になる、Poisson の Lambda が 0 以下になる、Uniform の Max が Min 以下になる、といった場合が該当します2

定義した列はすべて出力データセットの列になります。中間計算のための列だけを出力から外す設定はありません。

式の構文

式は、分布のパラメータに書くテキストで、評価すると数値になります。

式は同じ定義の中の他の列を名前で参照できます。参照に循環がなければ、列を並べる順は問いません。数値の列は名前をそのまま書いて参照します。文字列の列(Categorical の列と Add Factor で作る因子の列)は、後述の cases 経由でしか参照できません。

使える演算子は四則演算 + - * / と単項マイナス、比較 < <= > >= です。優先順位は乗除、加減、比較の順に低くなり、括弧で順序を明示できます。比較は真なら 1、偽なら 0 を返します3。返り値が数値なので、比較を他の項と掛けて 0/1 の指示変数として使えます。

数学の記法のように比較を 2 つ続けて書くことはできず、0 < x < 1 はパースエラーになります。区間は 2 つの比較の積として (0 < x) * (x < 1) と書きます。=== は使えません4。単一の値との一致も (t >= 6) * (t <= 6) のように 2 つの比較の積で書きます。

使える関数と引数の個数は次のとおりです。

関数引数の個数意味
exp(x)1指数関数
log(x)1自然対数
sqrt(x)1平方根
logistic(x)1ロジスティック関数 1/(1+exp(−x))
pow(x, y)2べき乗 x^y
min(x, y)22 つの値の小さい方
max(x, y)22 つの値の大きい方
abs(x)1絶対値

cases は文字列の列の値ごとに式を切り替えます。cases(group){A: 0, B: 1.5, default: 0} のように、参照する列名と、水準ごとの式を書きます。水準をすべて並べるか、default の項目を置く必要があります。水準名は、英字または _ で始まり英数字と _ が続く形であればそのまま書けます。それ以外の水準名は cases(group){"Group A": 0, default: 1} のように引用符で囲みます。

cases の返り値は水準ごとの値そのものです。10 + cases(group){control: 0, treat: 1.5} のように基準となる式に足すと、群ごとのずれを表せます。

cases は水準を量的な値へ写す用途にも使えます。Deterministic の Value に cases(dose){low: 10, mid: 20, high: 40} と書くと、用量を数値として持つ列ができます。

lag(列, k) は同じ系列の k 行前の値を返します。系列の定義は 因子と行の構造 を参照してください。lag は Time column を宣言したときだけ使えます。オフセット k は 1 以上、Time column の Length 未満の整数です。0.3 + 0.5*lag(y, 1) + 0.2*lag(y, 2) のように、複数の過去を参照する式も書けます。

因子列と、By に時刻列を含まない列は、値が系列の中で一定なので lag の対象にできません。例えば水準 A の系列では、因子列はどの行でも A で、k 行前の値も A のままです。MIDAS は、2 つの列が互いの lag を参照し合う定義を循環参照として拒否します。

系列の先頭より前を指す lag は 0 を返します。このため、自己回帰の系列は先頭の数行が以降の行と違う分布に従います。先頭の影響を避けたいときは、Length を長めにして先頭の時点を除いて使います。

式の例

よく使う式を示します。

目的書く場所
単回帰y の Mean1 + 2*x
交互作用y の Mean1 + 0.5*x1 + 0.3*x2 + 0.2*x1*x2
ポアソン回帰Poisson の Lambdaexp(0.5 + 0.3*x)
群ごとの切片のずれy の Mean10 + cases(group){control: 0, treat: 1.5}
x で変わる散らばりy の SD0.5 + 0.2*abs(x)
値の範囲の切り詰めDeterministic の Valuemin(max(z, -2), 2)

因子と行の構造

Factors を宣言すると、行数は因子から決まります。Rows 欄は入力を受け付けなくなり、決まった行数を表示します。行数は、すべての因子の水準数を掛け合わせた値に、Rows per cell と Time column の Length を掛けた値です。10,000,000 行を超える定義は生成できません。

Add Factor で作る因子は、宣言した水準を値に持つ文字列の列を 1 本作ります。Name に列名、Levels にカンマ区切りで水準を書きます。因子を複数宣言すると、水準のすべての組み合わせが行として並びます。Rows per cell は 1 つの組み合わせあたりの行数を決めます。水準の全組み合わせに同じ行数を割り当てるため、均衡したデータを作れます。

Time column に名前を書くと、1 から Length までの整数を値に持つ列ができます。水準の組み合わせと Rows per cell で決まる 1 行ずつが、時刻 1 から Length までの行に展開されます。この展開でできた行のまとまりを系列と呼びます。行は系列ごとに時刻の順に並び、lag は同じ系列の中で過去を参照します。時刻の列は数値なので、0.1*t のように時刻を使った項を式に書けます。

因子の列と時刻の列も出力データセットの列になります。

因子を宣言せず Time column だけを使う場合、Rows per cell を 2 以上にすると、各時点に Rows per cell 個の観測を持つデータができます。By に時刻列を指定した列と組み合わせると、同じ時点の観測が共通の値を共有するデータを作れます。この構成では系列が Rows per cell 本でき、lag は系列ごとに独立に過去を参照します。どの行がどの系列に属するかを示す列はできないため、観測のまとまりを区別する列が必要なときは因子を宣言します。

By と群ごとの値

By を指定した列は、群ごとに 1 回だけ値を生成し、その群のすべての行に同じ値を入れます。群ごとの切片のずれなど、群ごとに決まる値を作るのに使います。

群は By に並べた列の値の組で決まります。By に指定できるのは、因子・Time column・Categorical 列の名前だけです。連続値の列は指定できません。因子を指定すると、群の数は宣言どおりで、群の大きさは均等になります。Categorical 列を指定すると、各群の行数はサンプリングの結果で決まるため一定になりません。行数によっては 1 行も現れない水準が生じます。

因子の一部だけを By に並べた列は、その値を、並べなかった因子をまたいで共有します。たとえば school と class の 2 因子があるとき、By に class だけを書いた列は、同じ class の値をすべての school で共有します。school ごとに別の値を生成する入れ子の群にするには、By に school, class と両方を並べます。

By を持つ列の式が参照できるのは、By に並べた列と、その By がこの列の By の部分集合である列だけです。観測ごとに値が変わる列を参照すると生成が失敗します。By を持つ列では lag も使えません。

Time column の名前を By に指定すると、時点ごとに 1 回だけ値を生成する列になります。同じ時点の値は全系列で共有します。

By で作った群ごとの値を、固定効果として扱うかランダム効果として扱うかは、当てはめるモデル側の指定で決まります。考え方は GLMM の基礎 を参照してください。

プリセット

Preset を選ぶと、因子と列がプリセットの内容に置き換わり、編集の出発点になります。Dataset name と Seed はそのまま残ります。Preset を選び直すと、それまでの因子と列の編集内容とプレビューは消えます。既存のデータセットを編集しているときは、Preset は選べません。

Multilevel (random intercept) は 40 校 × 10 人の 400 行です。学校ごとの切片 u を SD 0.8 の正規分布から生成し、個人ごとの説明変数 x から y = 10 + 0.6x + u に SD 1 の残差を加えます。x を与えたときの 級内相関係数 は 0.64/(0.64+1) ≈ 0.39 です。

Repeated measures (subject × time) は 30 人 × 8 時点の 240 行です。個人ごとの切片 u を SD 1 の正規分布から生成し、y = 20 + 0.5t + u に時点ごとに独立な SD 1 の測定誤差を加えます。同一個人内の時点間相関は 0.5 で、系列相関はありません。

Correlated random intercept and slope は 40 群 × 10 行の 400 行です。群ごとの切片 u0(SD 0.9)と傾き u1(SD 0.4)を相関 0.5 で生成し、y = 2 + u0 + (0.7 + u1)x に SD 1 の残差を加えます。相関する 2 つの効果は、独立な標準正規 z0・z1 の線形結合として合成します。

MIDAS の GLMM が当てはめるのはランダム切片だけです。そのため、Correlated random intercept and slope が作るデータにランダム切片モデルを当てはめると、モデルの構造が生成過程と食い違います。この当てはめでは y の条件付き分散が x に依存します。当てはめの操作は GLMM タブ を参照してください。

設定例

この節の各例は、生成過程の説明と、それを表現する設定の一覧を示します。

二値の応答

線形予測子を Deterministic 列に置き、logistic を通した値を Bernoulli の P にします。次の設定は、切片 −1、係数 0.8 のロジスティック回帰に従うデータを作ります。

分布パラメータBy
xNormalMean: 0、SD: 1
etaDeterministicValue: -1 + 0.8*x
yBernoulliP: logistic(eta)

群ごとに切片が違う回帰

因子で群を作り、群ごとに生成した By 列を平均に足します。次の設定は、Levels を A, B, C, D, E、Rows per cell を 40 とした因子 group の下で、群ごとの切片のずれ u を持つ回帰データを作ります。

分布パラメータBy
uNormalMean: 0、SD: 0.8group
xNormalMean: 0、SD: 1
yNormalMean: 10 + 0.6*x + u、SD: 1

自己回帰のある時系列

Time column を宣言し、y の Mean に lag(y, 1) を入れます。次の設定は、Time column を t、Length を 200 として、自己回帰係数 0.7 の系列を作ります。

分布パラメータBy
yNormalMean: 0.7 * lag(y, 1)、SD: 1

先頭行の lag は 0 を返すため、系列の先頭の数時点は、以降の時点より分散が小さくなります。この設定は 1 本の系列を 1 列に生成するため、そのまま ARIMA タブ に渡せます。

個体をまたぐパネル

因子で個体を宣言し、個体ごとに生成した By 列を平均に足します。次の設定は、Levels に 20 個体の識別子(P01, P02, ..., P20)を並べた因子 id と、Length 10 の Time column t の下で、個体 × 時点のパネルデータを作ります。

分布パラメータBy
uNormalMean: 0、SD: 1id
yNormalMean: 5 + 0.3*t + u、SD: 1

打ち切りのある生存時間

イベント時刻と打ち切り時刻をそれぞれ別の列として生成し、min で観測時間の列を、比較でイベント変数の列を作ります。次の設定は、イベント時刻の Scale を exp(0.5 + 0.3*x) とし、説明変数 x がイベント時刻に影響する生存時間データを作ります。

分布パラメータBy
xNormalMean: 0、SD: 1
T_eventWeibullShape: 1.5、Scale: exp(0.5 + 0.3*x)
T_censUniformMin: 0.5、Max: 3
timeDeterministicValue: min(T_event, T_cens)
eventDeterministicValue: T_event <= T_cens

event は式の最上位が比較なので 0/1 の int64 列になり、そのまま Kaplan-Meier タブ のイベント変数に使えます。打ち切り時刻には正の値だけを取る分布を使います5

保存したデータセットの編集

保存した合成データの定義は、データセットの Edit Operation から開き直せます。開く手順は Project Overview タブProject Lineage タブ を参照してください。

編集モードではデータセット名を変えられず、Update Dataset が同じデータセットを上書きします。名前を変えていない列は上書き後も同じ列 ID を保ちます。そのため、このデータセットを使うモデル・派生データセット・レポートは、列の参照を保ったままになります。編集しているデータセットを使うモデル・派生データセット・レポートがあるときは、タブの先頭に警告が出ます。

保存した合成データは、データ本体ではなく生成の定義と Seed を保持し、プロジェクトを開くたびに定義からデータを再生成します。再生成の値は乱数生成と数学関数の実装に依存するため、別のブラウザで開くか、MIDAS またはブラウザのバージョンが変わると、同じ定義と Seed でも値が変わることがあります。値をそのまま残したいときは、CSV へ書き出して読み込み直します。書き出しの操作は エクスポート を参照してください。

補遺: 式の文法と意味論

この補遺は、式のテキスト構文と評価規則を定義します。

文法

式の文法を EBNF で示します。

式           = 加減式 [ 比較演算子 加減式 ] ;
比較演算子   = "<" | "<=" | ">" | ">=" ;
加減式       = 項 { ("+" | "-") 項 } ;
項           = 基本式 { ("*" | "/") 基本式 } ;
基本式       = 数値 | 列参照 | 関数呼び出し | cases式 | lag式
             | "(" 式 ")" | ("-" | "+") 基本式 ;
関数呼び出し = 関数名 "(" 式 { "," 式 } ")" ;
関数名       = "exp" | "log" | "sqrt" | "logistic"
             | "pow" | "min" | "max" | "abs" ;
cases式      = "cases" "(" 識別子 ")" "{" 分岐 { "," 分岐 } [ "," ] "}" ;
分岐         = ラベル ":" 式 ;
ラベル       = 識別子 | 文字列 | 数値 | "default" ;
lag式        = "lag" "(" 識別子 "," 数値 ")" ;
列参照       = 識別子 ;
識別子       = (英字 | "_") { 英字 | 数字 | "_" } ;
数値         = ( 数字列 [ "." { 数字 } ] | "." 数字列 ) [ 指数部 ] ;
指数部       = ("e" | "E") [ "+" | "-" ] 数字列 ;
文字列       = '"' { '"' 以外の文字 } '"' | "'" { "'" 以外の文字 } "'" ;

トークンの間の空白(スペース・タブ・改行)は無視します。

a < b < c のように比較を 2 つ続けて書くと、パースエラーになります。括弧の中・関数の引数・cases の分岐はそれぞれ独立した式なので、そこには比較を書けます。= は字句解析の時点で拒否し、エラーメッセージで使える比較演算子を案内します。

負の数のリテラルはありません。-1 は、単項マイナスを数値 1 に適用した式として読みます。

数値のリテラルは有限の値だけを受理し、オーバーフローする表記(1e999 など)は字句解析の時点で拒否します。

cases は、同じラベルの重複と、default の 2 回以上の出現をパースエラーにします。数値のラベルは数値として読んでから文字列へ戻すため、01 は水準 "1" の分岐になります。字面どおりに照合するには引用符で囲みます。

cases と lag は、直後に ( が続くときだけ構文として扱います。続かなければ通常の列参照です。そのため、cases や lag という名前の列も参照できます。

関数の引数の個数は、パースの時点で検査します。

意味論

式は行ごとに評価し、値は IEEE 754 の倍精度浮動小数点数です。列参照は同じ行の値を読みます。分布のパラメータとして使う場合は、行ごとにパラメータの式を評価してから、その値で 1 つサンプリングします。By を持つ列では、群の最初の行で 1 回だけ評価とサンプリングを行います。

四則演算は倍精度の算術です。0 での除算は IEEE 754 に従って無限大に、0/0 は NaN になります。

比較は真なら 1、偽なら 0 です。比較する値のどちらかが NaN のときは NaN を返します。偽(0)へ潰すと、定義域外の計算の結果が有効な値として列に入り、検出できなくなるためです。

関数は倍精度の数学関数です。log と sqrt は負の引数に NaN を返し、log(0) は負の無限大になります。

cases の値は、その行の水準に対応する分岐の式の値です。水準がどの分岐にもなく default があるときは、default の式の値です。

lag の値は、同じ系列の k 行前の値です。系列の先頭より前は 0 で、系列の境界を越えて前の系列の値を読むことはありません。

式の評価そのものは NaN や無限大を許します。その値を分布のパラメータとして使った時点で MIDAS は有限性を検査し、非有限値であれば生成を失敗させます。

脚注

  1. Deterministic 列は、式の最上位が比較のときだけ 0/1 の int64 列になります。打ち切りのある生存時間 のイベント変数の列がこの例です。

  2. 線形予測子を定義域へ写すには、logistic で 0 から 1 の範囲に、exp で正の値に変換します。

  3. 比較する 2 つの値のどちらかが NaN のときは、0 でも 1 でもなく NaN を返します。NaN をパラメータに使った時点で生成が失敗するため、定義域外の計算が 0 や 1 として列に紛れることはありません。

  4. 浮動小数点の等値比較は丸め誤差で意図しない結果を生むため、言語に含めていません。

  5. 観測時間が 0 以下の行があると、生存分析はデータセットを拒否します。