オーディエンス リストの回帰モデリング

既存の線形回帰モデルまたはロジスティック回帰モデルを使用することで、ML.PREDICT を使用せずに、既知の重み付けによる予測を行うことができます。モデル自体へのアクセスも不要です。これを行うためには、Ads Data Hub でのオーディエンスの有効化クエリ内で、差分プライベート化(DP)の回帰モデルを使用するための対処法を講じる必要があります。

手順の例を参照しながら、実際の線形回帰モデルやバイナリ ロジスティック回帰モデルのシミュレーション予測を実行する方法を説明します。また、その結果を ML.PREDICT の結果と比較して、シミュレーション結果の精度を把握する方法も説明します。実践的な例として、コンバージョン モデルをオーディエンスの有効化に適用する際に使用されるバイナリ ロジスティック モデルによって、オーディエンス リストを作成する方法も紹介します。

例の概要:

  1. データの生成
  2. モデルのトレーニング
  3. 重み付けと切片の取得
  4. 予測のシミュレーション
  5. 結果の比較

手順の例

1. データの生成

モデルをトレーニングするためのシミュレーション データを含むテーブルを作成します。ホールドバック セット用に一部の行をマークします。

線形回帰

CREATE OR REPLACE TABLE DATASET_NAME.LIN_REG_TRAINING_SET AS
  WITH
  A AS (
    SELECT
      *
    FROM
      UNNEST(GENERATE_ARRAY(1, 100000)) AS row_number),
  B AS (
    SELECT
      row_number,
      RAND() AS rand_label,
      RAND() AS rand_feature_1,
      RAND() AS rand_feature_2,
      RAND() AS rand_feature_3,
      RAND() AS rand_feature_4,
      RAND() AS rand_feature_5,
      RAND() AS rand_feature_6,
      RAND() AS rand_feature_7,
      RAND() AS rand_feature_8,
      RAND() AS rand_feature_9,
      RAND() AS rand_feature_10
    FROM
      A),
  C AS (
    SELECT
      rand_label AS label,
      *
    FROM
      B),
  D AS (
    SELECT
    row_number,
    CAST(round(10 * label) AS INT64) AS label,
    (rand_label + rand_feature_1) / 2 AS feature_1,
    (rand_label + rand_feature_2) / 2 AS feature_2,
    (rand_label + rand_feature_3) / 2 AS feature_3,
    (rand_label + rand_feature_4) / 2 AS feature_4,
    (rand_label + rand_feature_5) / 2 AS feature_5,
    (rand_label + rand_feature_6) / 2 AS feature_6,
    (rand_label + rand_feature_7) / 2 AS feature_7,
    (rand_label + rand_feature_8) / 2 AS feature_8,
    (rand_label + rand_feature_9) / 2 AS feature_9,
    (rand_label + rand_feature_10) / 2 AS feature_10
    FROM
    C)

SELECT
  label,
  feature_1,
  feature_2,
  feature_3,
  feature_4,
  feature_5,
  feature_6,
  feature_7,
  feature_8,
  feature_9,
  feature_10,
  RAND() < 0.1 AS holdback -- Ten percent will be true.
FROM
  D

バイナリ ロジスティック回帰

SELECT
  CASE
    WHEN label < 5 THEN 0
    WHEN label >= 5 THEN 1
  END
  AS label,
  * EXCEPT (label)
FROM
  `DATASET_NAME.BIN_LOG_REG_TRAINING_SET`

2. モデルのトレーニング

トレーニング セットを基に回帰モデルをトレーニングします。

線形回帰

CREATE OR REPLACE MODEL `DATASET_NAME.LIN_REG_MODEL` OPTIONS (model_type="linear_reg") AS
  SELECT
    * except (holdback)
  FROM
    `DATASET_NAME.LIN_REG_TRAINING_SET`
  WHERE
    NOT holdback

なお、決定係数 = 0.9009 として、十分なノイズをシミュレーション データに追加してモデルを取得できるようにしています。

測定対象
平均絶対誤差 0.7359
平均二乗誤差 0.8432
平均二乗対数誤差 0.0810
絶対誤差の中央値 0.6239
決定係数 0.9009

バイナリ ロジスティック回帰

CREATE OR REPLACE MODEL `DATASET_NAME.BIN_LOG_REG_MODEL` OPTIONS (model_type="logistic_reg") AS
  SELECT
    * EXCEPT (holdback)
  FROM
    `DATASET_NAME.BIN_LOG_REG_TRAINING_SET`
  WHERE
    NOT holdback

結果の例です。精度は 0.9260 です。

測定対象
陽性クラス 1
陰性クラス 0
適合率 0.0810
再現率 0.9315
精度 0.9260
F1 スコア 0.9328

以下の混同行列内の太字の値は、モデルによって各ラベルが正しく分類された頻度を表し、太字以外の値は、モデルによって各ラベルが誤って分類された頻度を表しています。

True ラベル 予測ラベル 1 予測ラベル 2
1 93% 7%
0 8% 92%

3.重み付けと切片の取得

モデルの重み付けと切片を取得します。

線形回帰

SELECT
  *
FROM
  ML.WEIGHTS(MODEL `DATASET_NAME.LIN_REG_MODEL`)
重み付け category_weights.category
feature_1 1.8263055528635743
feature_2 1.8143804404490813
feature_3 1.8601204874033492
feature_4 1.8507603439031859
feature_5 1.7899764387123640
feature_6 1.8645246630251291
feature_7 1.8698005281925356
feature_8 1.7904637080330201
feature_9 1.8036887855406274
feature_10 1.8117115890624449
INTERCEPT -4.1428754911504306

バイナリ ロジスティック回帰

SELECT
  *
FROM
  ML.WEIGHTS(MODEL `DATASET_NAME.BIN_LOG_REG_MODEL`)
重み付け category_weights.category
feature_1 3.823533928
feature_2 3.734812819
feature_3 3.842239823
feature_4 3.785488823
feature_5 3.737386716
feature_6 3.567663961
feature_7 3.819643052
feature_8 3.734673763
feature_9 3.839301406
feature_10 3.787306994
INTERCEPT -17.922169920

4. 予測のシミュレーション

線形回帰

特徴値と重み付けのドット積を使用し、切片を追加して、ML.PREDICT を使用せずに標準 SQL で予測を行います。このクエリは、この手法による予測と ML.PREDICT による予測を比較します。SQL 行の太字部分によって、行の特徴値とモデルの重み付けのドット積が求められ、切片が追加されます。

WITH
T AS (
SELECT
  label AS actual_label,
  predicted_label AS ml_predicted_label,
  [feature_1,
  feature_2,
  feature_3,
  feature_4,
  feature_5,
  feature_6,
  feature_7,
  feature_8,
  feature_9,
  feature_10] AS features,
  [1.8263055528635743,
  1.8143804404490813,
  1.8601204874033492,
  1.8507603439031859,
  1.789976438712364,
  1.8645246630251291,
  1.8698005281925356,
  1.7904637080330201,
  1.8036887855406274,
  1.8117115890624449] AS weights
FROM
  ML.PREDICT(MODEL `DATASET_NAME.LIN_REG_MODEL`,
    (
    SELECT
      *
    FROM
      `PROJECT_NAME.DATASET_NAME.LIN_REG_TRAINING_SET`))
WHERE
  holdback),
P AS (
SELECT
  actual_label,
  ml_predicted_label,
  (
   SELECT
    SUM(element1 * element2) - 4.1428754911504306
  FROM
    T.features element1
  WITH
  OFFSET
    pos
  JOIN
    T.weights element2
  WITH
  OFFSET
    pos
  USING
    (pos) ) sql_predicted_label,
  features,
  weights
FROM
  T)
SELECT
  actual_label,
  ml_predicted_label,
  sql_predicted_label,
  ABS(ml_predicted_label - sql_predicted_label) < 0.00000000001 AS diff_is_negligible
FROM
  P

バイナリ ロジスティック回帰

バイナリ ロジスティック回帰の場合、予測のシミュレーション手法は線形回帰とよく似ていますが、最終ステップに、所定のしきい値でシグモイド関数が追加で適用されます。

特徴値と重み付けのドット積を使用し、切片を追加して、ML.PREDICT を使用せずに標準 SQL で予測を行います。次に、結果に対してしきい値 0.5 のシグモイド関数を使用して、0 または 1 を予測します。このクエリは、この手法による予測と ML.PREDICT による予測を比較します。

WITH
T AS (
SELECT
  label AS actual_label,
  predicted_label AS ml_predicted_label,
  [feature_1,
  feature_2,
  feature_3,
  feature_4,
  feature_5,
  feature_6,
  feature_7,
  feature_8,
  feature_9,
  feature_10] AS features,
  [3.8235339279050287,
  3.7348128191185244,
  3.8422398227859471,
  3.7854888232502479,
  3.7373867156553713,
  3.5676639605351026,
  3.8196430517007811,
  3.7346737628343032,
  3.8393014063170749,
  3.7873069939244743] AS weights
FROM
  ML.PREDICT(MODEL `DATASET_NAME.BIN_LOG_REG_MODEL`,
    (
    SELECT
      *
    FROM
      `PROJECT_NAME.DATASET_NAME.BIN_LOG_REG_TRAINING_SET`))
WHERE
  holdback),
P AS (
SELECT
  actual_label,
  ml_predicted_label,
  (
   SELECT
    IF((1 / (1 + EXP(-(SUM(element1 * element2) -17.922169920432161)))) < 0.5, 0, 1)
  FROM
    T.features element1
  WITH
  OFFSET
    pos
  JOIN
    T.weights element2
  WITH
  OFFSET
    pos
  USING
    (pos) ) sql_predicted_label,
  features,
  weights
FROM
  T)
SELECT
  actual_label,
  ml_predicted_label,
  sql_predicted_label,
  ml_predicted_label = sql_predicted_label AS simulation_is_accurate
FROM
  P

上のクエリでは、SQL コードの太字部分のブロックで、各行の特徴値とモデルの重み付けのドット積を求め、インターセプトを追加して線形回帰の予測を行っています。

IF((1 / (1 + EXP(-(SUM(element1 * element2) -17.922169920432161)))) < 0.5, 0, 1)

次に、標準 SQL を使用して、シグモイド関数 Y = 1 / (1+e^-z) をドット積と切片に適用します。

IF((1 / (1 + EXP(-(SUM(element1 * element2) -17.922169920432161)))) < 0.5, 0, 1)

最後に、シグモイド関数の結果がしきい値 0.5 と比較され、0.5 未満の場合は 0、そうでない場合は 1 というバイナリ ロジスティック回帰予測に到達します。しきい値には、0~1 の任意の値を使用できます。

IF((1 / (1 + EXP(-(SUM(element1 * element2) -17.922169920432161)))) < 0.5, 0, 1)

この手法は、マルチクラス ロジスティック回帰にも応用できます。その場合、モデルの重み付けはベクトルではなく nxn 行列になり、重み付けはスカラーではなくベクトルになります。特徴値のベクトルに重み付けの行列を掛けて、切片のベクトルを追加します。結果として導出されるベクトルには各ラベルのスコアが含まれ、予測には最もスコアが高いラベルを選択できます。確率配列を返す場合は、配列の各要素にシグモイド関数を適用します。

5. 結果の比較

線形回帰

小さな丸め誤差を除き、サンプルの結果はほぼ同じです。

actual_label ml_predicted_label sql_predicted_label diff_is_negligible
6 5.2062349420751834 5.2062349420751826 true
0 0.40318472770048075 0.403184727700479 true
3 3.0703766078249597 3.0703766078249597 true
7 7.0588171538562 7.0588171538562 true
6 6.7802375930646 6.7802375930646 true
6 5.1088569571339368 5.1088569571339377 true
4 4.051839078116874 4.051839078116874 true
4 5.1810254680219243 5.1810254680219234 true
6 6.1440349466401223 6.1440349466401205 true
1 2.0842399472783519 2.0842399472783519 true
2 2.1911209811886847 2.1911209811886838 true
3 3.0236086790006622 3.0236086790006613 true
2 2.573083132964213 2.5730831329642125 true
7 5.68662973136732 5.6866297313673186 true
9 8.1860026312677938 8.1860026312677938 true

バイナリ ロジスティック回帰

シミュレーション予測と ML.PREDICT の実際の結果を比較すると、完全に一致しており、10,000 行のホールドバック セット内に不一致が 1 つもありません。ML.PREDICT とシミュレーション予測の両方が実際のラベルと一致していない行がいくつかありますが、これはモデルの精度が約 93% であるため予想されたことです。また、混同行列の非対角セルに、ゼロではない小さい値があります。

actual_label ml_predicted_label sql_predicted_label simulation_is_accurate
0 1 1 true
0 0 0 true
0 0 0 true
0 0 0 true
0 0 0 true
0 0 0 true
0 0 0 true
0 0 0 true
0 0 0 true
0 0 0 true
0 1 1 true
0 0 0 true

ML によるオーディエンスの有効化リストの作成

ユースケースとしては、コンバージョンを予測するための差分プライベート バイナリ ロジスティック回帰モデルを作成してから、オーディエンス リストを作成する際にこのモデルで予測を適用する方法が一般的です。前提として、上記の例で作成したバイナリ ロジスティック モデルはコンバージョンのモデリングを行い、トレーニング セットと評価セットの各行は個々のユーザーを表すものとします。

次のクエリは、モデルによって、コンバージョンに至ると予測されたユーザーで構成されるオーディエンス リストを作成する方法を示しています。

WITH
T AS (
SELECT
  *,
  label AS actual_label,
  [feature_1,
  feature_2,
  feature_3,
  feature_4,
  feature_5,
  feature_6,
  feature_7,
  feature_8,
  feature_9,
  feature_10] AS features,
  [3.8235339279050287,
  3.7348128191185244,
  3.8422398227859471,
  3.7854888232502479,
  3.7373867156553713,
  3.5676639605351026,
  3.8196430517007811,
  3.7346737628343032,
  3.8393014063170749,
  3.7873069939244743] AS weights
FROM
  `PROJECT_NAME.DATASET_NAME.BIN_LOG_REG_TRAINING_SET`
WHERE
  holdback),
P AS (
SELECT
  *,
  (
  SELECT
  IF
    ((1 / (1 + EXP(-(SUM(element1 * element2) -17.922169920432161)))) < 0.5, 0, 1)
  FROM
    T.features element1
  WITH
  OFFSET
    pos
  JOIN
    T.weights element2
  WITH
  OFFSET
    pos
  USING
    (pos) ) predicted_label,
  features,
  weights
FROM
  T),
SELECT
  user_id
FROM
  P
WHERE
  predicted_label = 1;