2
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

[Oracle Cloud] Autonomous Database+OMLノートブックで機械学習してみた(PL/SQL編)

Posted at

はじめに

Autonomous Databaseには、Oracle Machine Learningユーザー・インタフェースが用意されており、OML Notebooks、OML AutoML UI、OML Models、テンプレート・サンプル・ノートブックなどのOracle Machine Learningのコンポーネントおよび機能にすばやくアクセスできます。
OML Notebooks(ノートブック)を使用してPL/SQLを使った機械学習をしてみました。

OML ノートブック

モデル開発用の共同共有ワークスペースとして提供され、Autonomous Database内のすべてのデータへの直接接続します。
データおよび機械学習の結果を表示するビジュアル・パレットがあり、ディスカッション、ドキュメント、実行および結果が一緒に表示される共有プラットフォームです。

利用するには、Autonomous DatabaseのユーザでOMLを有効化します。
image.png

サンプルシナリオ

SQL Developer に含まれるチュートリアル用データを使います。
以下のスクリプトを作ってサンプルデータを作成します。

alter session set nls_date_language = 'AMERICAN';
@C:\sqldeveloper\dataminer\scripts\instInsurCustData.sql {username}

INSUR_CUST_LTV_SAMPLE表は、保険商品を購入したかしなかったか結果が入った顧客情報表です。
BUY_INSURANCE列を教師データとして、分類モデル3つのアルゴリズムで作成し、モデルを比較します。
精度のよいモデルを使って予測を実施します。

OMLノートブックをはじめる

データベース・アクションでOML UIの起動

image.png
OMLを有効化したユーザでログイン
image.png

image.png

左上のハンバーガーメニューから「プロジェクト」>「ノートブック」を選択
image.png

ノートブックの作成

[作成」をクリックし、名前を入力しノートブックを作成します。
image.png

作成したノートブックを選択しノートブックを起動します。

データの確認

教師データの確認

%sql
SELECT * FROM INSUR_CUST_LTV_SAMPLE WHERE ROWNUM < 50;

image.png

ターゲット列の値のサマリ

%sql

SELECT BUY_INSURANCE, COUNT(*)
FROM INSUR_CUST_LTV_SAMPLE
GROUP BY BUY_INSURANCE

image.png

ボタンをクリックしグラフ表示が可能
image.png

顧客情報 (MARITAL_STATUS列)

SELECT MARITAL_STATUS, COUNT(*) 
FROM INSUR_CUST_LTV_SAMPLE
GROUP BY MARITAL_STATUS;

image.png

BUY_INSURANCEの値に影響がある列の調査

%script 
BEGIN DBMS_DATA_MINING.DROP_MODEL('ai_explain_output_buy_insur_bin');
EXCEPTION WHEN OTHERS THEN NULL; END;

DECLARE
    v_setlst DBMS_DATA_MINING.SETTING_LIST;
BEGIN
    v_setlst('ALGO_NAME')        := 'ALGO_AI_MDL';
    V_setlst('PREP_AUTO')        := 'ON';

    DBMS_DATA_MINING.CREATE_MODEL2(
        MODEL_NAME        => 'ai_explain_output_buy_insur_bin',
        MINING_FUNCTION   => 'ATTRIBUTE_IMPORTANCE',
        DATA_QUERY        => 'select * from INSUR_CUST_LTV_SAMPLE',
        SET_LIST          => v_setlst,
        CASE_ID_COLUMN_NAME => 'CUSTOMER_ID',
        TARGET_COLUMN_NAME  => 'BUY_INSURANCE');
END;

image.png

BUY_INSURANCEの値に影響がある列の上位15を表示

%sql

SELECT * FROM DM$VAai_explain_output_buy_insur_bin WHERE ROWNUM <16;

image.png

DBMS_DATA_MINING_TRANSFORMS パッケージを使ったヒストグラムの作成

%script

-- Create a view that bins ALL the numeric columns.  

BEGIN

BEGIN 
EXECUTE IMMEDIATE 'DROP TABLE bin_num_tbl';
EXCEPTION WHEN OTHERS THEN NULL; 
END; 

BEGIN
EXECUTE IMMEDIATE 'DROP VIEW mining_data_bin_view';
EXCEPTION WHEN OTHERS THEN NULL; 
END; 


   dbms_data_mining_transform.create_bin_num(
           bin_table_name     => 'bin_num_tbl');

   dbms_data_mining_transform.insert_autobin_num_eqwidth(
           bin_table_name     => 'bin_num_tbl',
           data_table_name    => 'INSUR_CUST_LTV_SAMPLE',
           bin_num            => 5,
           max_bin_num        => 10,
           exclude_list       => dbms_data_mining_transform.COLUMN_LIST('CUSTOMER_ID'));

  dbms_data_mining_transform.xform_bin_num(
           bin_table_name      => 'bin_num_tbl',
           data_table_name     => 'INSUR_CUST_LTV_SAMPLE',
           xform_view_name     => 'mining_data_bin_view');
END;

image.png

ヒストグラムの表示 例:BANK_FUNDS

%sql

SELECT CUSTOMER_ID, AGE, SALARY, BANK_FUNDS, CREDIT_CARD_LIMITS, MORTGAGE_AMOUNT, LTV FROM MINING_DATA_BIN_VIEW;

image.png

モデルの作成

ディシジョンツリー(DT)、サポートベクターマシン(SVM)、ランダムフォレストのアルゴリズムを使ったモデルを作成します。

ディシジョンツリー(DT)モデルの作成

%script

BEGIN
  DBMS_DATA_MINING.DROP_MODEL('N2_CLASS_MODEL_DT');
  EXCEPTION WHEN OTHERS THEN NULL; 
END;
/
DECLARE
    v_setlst DBMS_DATA_MINING.SETTING_LIST;
BEGIN
    v_setlst('PREP_AUTO') := 'ON';
    v_setlst('ALGO_NAME') := 'ALGO_DECISION_TREE';
    DBMS_DATA_MINING.CREATE_MODEL2(
	MODEL_NAME        => 'N2_CLASS_MODEL_DT',
        MINING_FUNCTION   => 'CLASSIFICATION',
        DATA_QUERY        => 'SELECT * FROM INSUR_CUST_LTV_SAMPLE',
        SET_LIST          => v_setlst,
        CASE_ID_COLUMN_NAME => 'CUSTOMER_ID',
        TARGET_COLUMN_NAME  => 'BUY_INSURANCE');
END;

ディシジョンツリー(DT)モデルの評価値の計算

%script

-- Drop result tables
BEGIN
  EXECUTE IMMEDIATE 'DROP TABLE N2_APPLY_RESULT_DT PURGE';
  EXCEPTION WHEN OTHERS THEN NULL; 
END;
/
BEGIN
  EXECUTE IMMEDIATE 'DROP TABLE N2_LIFT_TABLE_DT PURGE';
EXCEPTION WHEN OTHERS THEN NULL; 
END;
/    
-- Score the data and compute lift
BEGIN
DBMS_DATA_MINING.APPLY('N2_CLASS_MODEL_DT','INSUR_CUST_LTV_APPLY','CUSTOMER_ID','N2_APPLY_RESULT_DT');
DBMS_DATA_MINING.COMPUTE_LIFT('N2_APPLY_RESULT_DT','INSUR_CUST_LTV_SAMPLE','CUSTOMER_ID','BUY_INSURANCE','N2_LIFT_TABLE_DT','Yes','PREDICTION','PROBABILITY',100);
END;

サポートベクターマシン(SVM)モデルの作成

%script

BEGIN
DBMS_DATA_MINING.DROP_MODEL('N2_CLASS_MODEL_SVM');
EXCEPTION WHEN OTHERS THEN NULL; 
END;
/

DECLARE
    v_setlst DBMS_DATA_MINING.SETTING_LIST;
BEGIN
    v_setlst('PREP_AUTO') := 'ON';
    v_setlst('ALGO_NAME') := 'ALGO_SUPPORT_VECTOR_MACHINES';
    v_setlst('SVMS_KERNEL_FUNCTION') := 'SVMS_GAUSSIAN';
    DBMS_DATA_MINING.CREATE_MODEL2(
	MODEL_NAME        => 'N2_CLASS_MODEL_SVM',
        MINING_FUNCTION   => 'CLASSIFICATION',
        DATA_QUERY        => 'SELECT * FROM INSUR_CUST_LTV_SAMPLE',
        SET_LIST          => v_setlst,
        CASE_ID_COLUMN_NAME => 'CUSTOMER_ID',
        TARGET_COLUMN_NAME  => 'BUY_INSURANCE');
END;

サポートベクターマシン(SVM)モデルの評価値の計算

%script

-- Drop result tables
BEGIN
  EXECUTE IMMEDIATE 'DROP TABLE N2_APPLY_RESULT_SVM PURGE';
  EXCEPTION WHEN OTHERS THEN NULL; 
END;
/
BEGIN
  EXECUTE IMMEDIATE 'DROP TABLE N2_LIFT_TABLE_SVM PURGE';
EXCEPTION WHEN OTHERS THEN NULL; 
END;
/
-- Score the data and compute lift
BEGIN
DBMS_DATA_MINING.APPLY('N2_CLASS_MODEL_SVM','INSUR_CUST_LTV_APPLY','CUSTOMER_ID','N2_APPLY_RESULT_SVM');
DBMS_DATA_MINING.COMPUTE_LIFT('N2_APPLY_RESULT_SVM','INSUR_CUST_LTV_SAMPLE','CUSTOMER_ID','BUY_INSURANCE','N2_LIFT_TABLE_SVM','Yes','PREDICTION','PROBABILITY',100);
END;

ランダムフォレスト(RM)モデルの作成

%script
BEGIN
DBMS_DATA_MINING.DROP_MODEL('N2_CLASS_MODEL_RF');
EXCEPTION WHEN OTHERS THEN NULL; 
END;
/

DECLARE
    v_setlst DBMS_DATA_MINING.SETTING_LIST;
BEGIN
    v_setlst('PREP_AUTO') := 'ON';
    v_setlst('ALGO_NAME') := 'ALGO_RANDOM_FOREST';
    DBMS_DATA_MINING.CREATE_MODEL2(
	MODEL_NAME        => 'N2_CLASS_MODEL_RF',
        MINING_FUNCTION   => 'CLASSIFICATION',
        DATA_QUERY        => 'SELECT * FROM INSUR_CUST_LTV_SAMPLE',
        SET_LIST          => v_setlst,
        CASE_ID_COLUMN_NAME => 'CUSTOMER_ID',
        TARGET_COLUMN_NAME  => 'BUY_INSURANCE');
END;
/

ランダムフォレスト(RM)モデルの評価値の計算

%script

-- Drop result tables
BEGIN
  EXECUTE IMMEDIATE 'DROP TABLE N2_APPLY_RESULT_RF PURGE';
  EXCEPTION WHEN OTHERS THEN NULL; 
END;
/
BEGIN
  EXECUTE IMMEDIATE 'DROP TABLE N2_LIFT_TABLE_RF PURGE';
EXCEPTION WHEN OTHERS THEN NULL; 
END;
/

-- Score the data and compute lift
BEGIN
DBMS_DATA_MINING.APPLY('N2_CLASS_MODEL_RF','INSUR_CUST_LTV_APPLY','CUSTOMER_ID','N2_APPLY_RESULT_RF');
DBMS_DATA_MINING.COMPUTE_LIFT('N2_APPLY_RESULT_RF','INSUR_CUST_LTV_SAMPLE','CUSTOMER_ID','BUY_INSURANCE','N2_LIFT_TABLE_RF','Yes','PREDICTION','PROBABILITY',100);
END;
/

モデルの比較

比較用ビューの作成

%script

CREATE OR REPLACE VIEW ALL_LIST_DATA_V AS
SELECT QUANTILE_NUMBER, GAIN_CUMULATIVE, CAST('DECISION_TREE' AS VARCHAR(50)) AS ALGO_NAME 
  FROM N2_LIFT_TABLE_DT
UNION
SELECT QUANTILE_NUMBER, GAIN_CUMULATIVE, CAST('SVM' AS VARCHAR(50)) AS ALGO_NAME 
  FROM N2_LIFT_TABLE_SVM
UNION 
SELECT QUANTILE_NUMBER, GAIN_CUMULATIVE, CAST('RANDOM_FOREST' AS VARCHAR(50)) AS ALGO_NAME 
  FROM N2_LIFT_TABLE_RF;

モデルの比較

%sql

SELECT A.ALGO_NAME, A.QUANTILE_NUMBER, ROUND(A.GAIN_CUMULATIVE*100,2) GAIN_CUMULATIVE, B.RANDOM_GUESS
FROM ALL_LIST_DATA_V A,
     (SELECT ALGO_NAME, QUANTILE_NUMBER, QUANTILE_NUMBER RANDOM_GUESS FROM ALL_LIST_DATA_V) B
WHERE A.QUANTILE_NUMBER = B.QUANTILE_NUMBER AND A.ALGO_NAME = B.ALGO_NAME;

image.png

今回の結果では、ランダムフォレストがよりよいモデルとなりました。

予測

新しい顧客にモデルを適用して、BUY_INSURANCEが「はい」になる可能性が高い顧客を予測
新しい顧客データがINSUR_CUST_LTV_APPLY表として用意

%sql 

SELECT CUSTOMER_ID, BUY_INSURANCE, PREDICTION(N2_CLASS_MODEL_RF USING *) PREDICTION, ROUND(PREDICTION_PROBABILITY(N2_CLASS_MODEL_RF, NULL USING *)*100,2) PROB_BUY_INSURANCE 
FROM   INSUR_CUST_LTV_APPLY 
ORDER BY PROB_BUY_INSURANCE DESC

image.png

データ可視化ツールで利用しやすいように、モデルの予測と確率で新しい表を作成します。

%script

BEGIN
  EXECUTE IMMEDIATE 'DROP TABLE BUY_INSUR_NEW_PREDICTIONS PURGE';
  EXCEPTION WHEN OTHERS THEN NULL; 
END;
/

CREATE TABLE BUY_INSUR_NEW_PREDICTIONS AS 
SELECT A.CUSTOMER_ID
	, A.PREDICTION
	, A.PROB_BUY_INSUR
	, B.STATE, B.AGE, B.SALARY, B.BANK_FUNDS, B.CREDIT_CARD_LIMITS, B.MORTGAGE_AMOUNT, B.LTV, B.MARITAL_STATUS
FROM (SELECT CUSTOMER_ID, PREDICTION(N2_CLASS_MODEL_RF USING *) PREDICTION, round(PREDICTION_PROBABILITY(N2_CLASS_MODEL_RF, 'Yes' USING *),2) PROB_BUY_INSUR FROM INSUR_CUST_LTV_APPLY) A
    , INSUR_CUST_LTV_APPLY B
WHERE A.CUSTOMER_ID = B.CUSTOMER_ID;

image.png

作成したBUY_INSUR_NEW_PREDICTIONS表から「Yes」の顧客をPROB_BUY_INSURでソートして確認します。
image.png

おわりに

OMLノートブックを使って結果をグラフ化しながら機械学習モデル作成、評価ができました。

参考情報

2
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
2
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?