🚒
Phi-3でSQL生成を試す
やりたいこと
この記事を見て、日本語が苦手かもとあったので、日本語使わないタスクならできそうかで、SQL生成を試してみます。
期待としては、CodeGenerateがzeroshotだとそれなりに良さそうなのと、
SQL生成となると速度が求められがちなので、SLMなら回答生成速度早いのかなーと。
試す
言語がenしか選べない。。
けど、適当に生成されたSQL生成のクエリを作成する.
サンプルプロンプト
次のように3つのテーブルが定義されています:
customers: 顧客情報を保存するテーブル。
customer_id (INT, 主キー): 顧客のユニークな識別子。
first_name (VARCHAR): 顧客の名。
last_name (VARCHAR): 顧客の姓。
orders: 顧客によって配置された注文を記録するテーブル。
order_id (INT, 主キー): 注文のユニークな識別子。
customer_id (INT): 注文をした顧客の識別子。
order_date (DATE): 注文が行われた日付。
total_amount (DECIMAL): 注文の合計金額。
order_items: 各注文に含まれるアイテムを含むテーブル。
item_id (INT, 主キー): アイテムのユニークな識別子。
order_id (INT): このアイテムを含む注文の識別子。
product_name (VARCHAR): 製品名。
quantity (INT): 注文された製品の数量。
price (DECIMAL): 製品の価格。
これらの三つのテーブルを結合して、各顧客ごとに注文された製品の合計数量と合計金額を見つけるSQLクエリを作成してください。
結果には顧客の名、姓、計算された合計が含まれるべきです。結果を顧客ごとにグループ化し、合計金額で降順に並べ替えてください。
出力
SELECT
c.first_name,
c.last_name,
SUM(oi.quantity) AS total_quantity,
SUM(oi.quantity * oi.price) AS total_amount
FROM
customers c
JOIN
orders o ON c.customer_id = o.customer_id
JOIN
order_items oi ON o.order_id = oi.order_id
GROUP BY
c.customer_id
ORDER BY
total_amount DESC;
サンプルプロンプト作成時に作成された、正解SQL
SELECT
c.first_name,
c.last_name,
SUM(oi.quantity) AS total_quantity,
SUM(oi.price * oi.quantity) AS total_amount
FROM customers c
JOIN orders o ON c.customer_id = o.customer_id
JOIN order_items oi ON o.order_id = oi.order_id
GROUP BY c.customer_id
ORDER BY total_amount DESC;
同じだ!
もうちょっと難しいのを生成してみる。
サンプルテキスト
以下の4つのテーブルがあるとします:
customers: 顧客情報を保持するテーブル。
customer_id (INT, 主キー): 顧客を一意に識別するID。
first_name (VARCHAR): 顧客の名前。
last_name (VARCHAR): 顧客の姓。
orders: 注文情報を保持するテーブル。
order_id (INT, 主キー): 注文を一意に識別するID。
customer_id (INT): 顧客IDを参照する外部キー。
order_date (DATE): 注文日。
status (VARCHAR): 注文の状態(例:'completed', 'pending'など)。
order_items: 注文された各アイテムを保持するテーブル。
item_id (INT, 主キー): アイテムを一意に識別するID。
order_id (INT): 注文IDを参照する外部キー。
product_id (INT): 製品IDを参照する外部キー。
quantity (INT): 注文された数量。
products: 製品情報を保持するテーブル。
product_id (INT, 主キー): 製品を一意に識別するID。
product_name (VARCHAR): 製品名。
price (DECIMAL): 製品の単価。
'completed'ステータスの注文に関連する製品の総売上と総利益(総売上から総コストを引いた値)を計算するSQLクエリを作成してください。
総売上は、各製品のpriceとquantityを掛け合わせた値の合計です。
総コストは、各製品のコスト(ここでは簡単のためpriceの半分とします)とquantityを掛け合わせた値の合計です。
結果には製品名、総売上、総利益を表示し、総売上の高い順に並べてください。
回答
SELECT
p.product_name,
SUM(oi.quantity * oi.price) AS total_sales,
SUM((oi.quantity * oi.price) - (oi.quantity * (oi.price / 2))) AS total_profit
FROM
orders o
JOIN
order_items oi ON o.order_id = oi.order_id
JOIN
products p ON oi.product_id = p.product_id
WHERE
o.status = 'completed
良さげだけど、途中でキレてる。。
サンプルプロンプトを作成時に作成された、正解SQL
SELECT
p.product_name,
SUM(oi.quantity * p.price) AS total_sales,
SUM(oi.quantity * p.price) - SUM(oi.quantity * (p.price / 2)) AS total_profit
FROM orders o
JOIN order_items oi ON o.order_id = oi.order_id
JOIN products p ON oi.product_id = p.product_id
WHERE o.status = 'completed'
GROUP BY p.product_name
ORDER BY total_sales DESC;
max_tokensを256にして、もう一回。
出力
SELECT
p.product_name,
SUM(oi.quantity * p.price) AS total_sales,
SUM(oi.quantity * (p.price / 2)) AS total_cost,
SUM(oi.quantity * (p.price - (p.price / 2))) AS total_profit
FROM
orders o
JOIN
order_items oi ON o.order_id = oi.order_id
JOIN
customers c ON o.customer_id = c.customer_id
WHERE
o.status = 'completed'
GROUP BY
p.product_name
ORDER BY
total_sales DESC;
なぜか、total_costを余計に出してくれたけど、おおむね良さそう。
あと、期待通り回答生成時間が早いです。全部生成されるまで、2.6秒とかでした。
複雑なSQLを書くならfewshotである必要があると思いますが、zeroshotだと結構使えるかも。
Discussion