クリーム色の背景、色付き表示、高コントラスト、大きな文字のほうが読みやすいですか?配色と文字を選ぶと、すべてのページに一度で反映されます。

無料レッスン

微調整のための学習データ

このレッスンのあとで: モデルが学べる学習用の例を書ける。

60分のレッスンコマンド6件AI コーディングエージェントのラボ:opencode でコードを説明・修正し、その結果を確かめる

学習データは、例の一覧

微調整(ファインチューニング)は、こちらが用意した例からモデルに学ばせることです。例は一組ずつで、モデルに渡すものと、返してほしいものからできています。

組がしていることは、モデルがそのまま真似します。だから、不注意な書き方を四十回繰り返すと、間違いを四十回教えることになります。

このレッスンのゴール

メモ

モデルが学べる学習用の例を書ける。

キーワード

ことばいみ
微調整自分たちの例で、モデルをさらに学習させること
prompt学習の組の、入力の半分
completion学習の組の、答えの半分
JSONL一行に JSON を一つずつ書くファイル
ラベル分類の名前になる、決まった言葉

学生が入力するセルは、このプレビューでは空白です。

一行に一組

JSONL のファイルは、一行に例を一つ入れます。各行は、prompt と completion を持つ小さな JSON のオブジェクトです。

一行だけを取り出して確かめることができます。90 行目が壊れていても、1 行目から 89 行目は使えます。学習用のファイルによくこの形が使われるのは、そのためです。

例: 三つの行

行中身判定
1prompt「二重に請求されました」、completion「billing」正しい
2prompt「請求書が違います」だけで、completion がないcompletion がない
3prompt「いいお店ですね」、completion「Other」知らないラベル。大文字が違う

学生が入力するセルは、このプレビューでは空白です。

形を、いつも同じにする

モデルは、組の中にある型を学びます。間違いも含めてです。「billing」が「Billing」や「請求」とも書かれていれば、三つの答えを覚えます。

ラベルは決まった一覧にして、綴りを一つずつ決め、プロンプトの形も一つにします。そのあとで、目ではなくプログラムでファイルを確かめます。

よくある間違い

注意

「例は多いほどよい」と考えがちです。きれいな 100 組は、ばらばらな 1,000 組より多くを教えます。モデルは間違いまで真似するからです。まずファイルを直し、それから増やします。

モデル用の補助を書く(1)

コマンド
docker exec -w /home/node/project agent sh -c "printf '%s\n' 'const base = process.env.AI_URL || \"http://ai:4000\";' '// 応答に含まれるトークン数。なければ null。' 'function count(data, name) {' '  return data.usage && typeof data.usage[name] === \"number\" ? data.usage[name] : null;' '}' > model.js"

ここでは表示のみで、実行されません。無料アカウントを作成すると、実行ボタンで自分のラボのターミナルに入力できます。

モデル用の補助を書く(2)

コマンド
docker exec -w /home/node/project agent sh -c "printf '%s\n' 'async function ask(messages, sample, max) {' '  try {' '    const res = await fetch(base + \"/v1/chat/completions\", {' '      method: \"POST\",' '      headers: { \"content-type\": \"application/json\", authorization: \"Bearer lab\" },' '      body: JSON.stringify({ model: \"lab\", messages: messages, max_tokens: max || 100 }),' '      signal: AbortSignal.timeout(30000),' '    });' '    if (res.ok === false) throw new Error(\"status \" + res.status);' '    const d = await res.json();' '    return { text: d.choices[0].message.content, inTokens: count(d, \"prompt_tokens\"), outTokens: count(d, \"completion_tokens\"), recorded: false };' '  } catch (error) {' '    console.log(\"記録済みサンプル: モデルが答えませんでした (\" + error.message + \")。\");' '    return { text: sample, inTokens: null, outTokens: null, recorded: true };' '  }' '}' 'module.exports = { ask };' >> model.js"

ここでは表示のみで、実行されません。無料アカウントを作成すると、実行ボタンで自分のラボのターミナルに入力できます。

行の検査を書く(1)

コマンド
docker exec -w /home/node/project agent sh -c "printf '%s\n' 'const { ask } = require(\"./model\");' 'const LABELS = [\"billing\", \"delivery\", \"other\"];' 'const lines = [' '  JSON.stringify({ prompt: \"二重に請求されました\", completion: \"billing\" }),' '  JSON.stringify({ prompt: \"荷物はどこですか\", completion: \"delivery\" }),' '  JSON.stringify({ prompt: \"いいお店ですね\", completion: \"Other\" }),' '  JSON.stringify({ prompt: \"請求書が違います\" }),' '  JSON.stringify({ prompt: \"\", completion: \"other\" }),' '  \"これは JSON ではありません\",' '  JSON.stringify({ prompt: \"箱がつぶれて届きました\", completion: \"delivery\" }),' '];' > adapt2.js"

ここでは表示のみで、実行されません。無料アカウントを作成すると、実行ボタンで自分のラボのターミナルに入力できます。

行の検査を書く(2)

コマンド
docker exec -w /home/node/project agent sh -c "printf '%s\n' 'function isText(v) {' '  return typeof v === \"string\";' '}' 'function isObject(v) {' '  return typeof v === \"object\" && v === null === false && Array.isArray(v) === false;' '}' 'function check(line) {' '  let row;' '  try { row = JSON.parse(line); } catch (e) { return \"JSON ではない\"; }' '  if (isObject(row) === false) return \"オブジェクトではない\";' '  if (isText(row.prompt) === false) return \"prompt がない\";' '  if (isText(row.completion) === false) return \"completion がない\";' '  if (row.prompt.trim() === \"\") return \"prompt が空\";' '  if (LABELS.includes(row.completion) === false) return \"知らないラベル\";' '  return \"\";' '}' >> adapt2.js"

ここでは表示のみで、実行されません。無料アカウントを作成すると、実行ボタンで自分のラボのターミナルに入力できます。

行の検査を書く(3)

コマンド
docker exec -w /home/node/project agent sh -c "printf '%s\n' 'async function main() {' '  let ok = 0;' '  lines.forEach(function (line, i) {' '    const why = check(line);' '    if (why === \"\") ok = ok + 1;' '    else console.log((i + 1) + \" 行目: \" + why);' '  });' '  console.log(lines.length + \" 行のうち \" + ok + \" 行が正しい\");' '  const q = \"学習データでラベルの書き方をそろえなければならないのは、なぜですか。短い一文で答えてください。\";' '  const sample = \"モデルは書き方の違いを別の答えとして覚えるので、ばらばらだと学ぶ内容も割れてしまうからです。\";' '  const reply = await ask([{ role: \"user\", content: q }], sample, 60);' '  console.log(\"返事: \" + reply.text);' '}' 'main();' >> adapt2.js"

ここでは表示のみで、実行されません。無料アカウントを作成すると、実行ボタンで自分のラボのターミナルに入力できます。

行の検査を実行する

コマンド
docker exec -w /home/node/project agent node adapt2.js

ここでは表示のみで、実行されません。無料アカウントを作成すると、実行ボタンで自分のラボのターミナルに入力できます。

検査で分かったこと

七つの行は架空のものです。検査は一行ずつ読み、最初に見つけた問題だけを言います。だから、問題を一つずつ直していけます。

最後の行は、短いモデルの呼び出しです。モデルが答えないときは、「記録済みサンプル」と表示します。

このラボとソースについて: AI コーディングエージェントのラボ:opencode でコードを説明・修正し、その結果を確かめる

授業で使いますか?このモジュールを学生に割り当てると、教員用ガイド、自動採点つきの課題、学生ごとのラボを使えます。