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

無料レッスン

埋め込みとコサイン類似度

このレッスンのあとで: 埋め込みとは何かを説明し、2つをコサイン類似度で比べられる。

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

同じ言葉が1つもないページ

埋め込み (エンベディング) とは、文章の意味を表す数のリストです。意味が近い文章は、同じ向きを指すリストになり、プログラムは計算で意味を比べられます。

図書館のサイトで、利用者が「本を持ち帰るルール」を探します。必要なページの題は「貸出の条件」です。同じ言葉が1つもないので、言葉だけの検索では見つかりません。数なら見つけられます。

このレッスンのゴール

メモ

埋め込みとは何かを説明し、2つをコサイン類似度で比べられる。

キーワード

ことばいみれい
埋め込み意味を表す、数のリスト
ベクトル点や矢印として見る、数のリスト
内積同じ位置の数を掛けて、全部足したもの
コサイン類似度2本の矢印が、どれだけ同じ向きかの点数0.98
検索質問に合う文章の断片を見つけること

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

本物の埋め込みと、この科目の代用品

本物の埋め込みは数百個の数でできていて、モデルが作ります。この科目では、1つも作りません。

代わりに、小さな代用品を使います。3つの数でできた作り物のリストと、スクリプトが自分で数える文字の回数です。こうすれば、各手順をここで実行して確かめられます。方法は同じです。

ベクトルは数のリスト

数のリストは、地図の上の点だと考えます。数が2つなら平らな地図の点、3つなら部屋の中の点です。

リストの各位置に意味を付けます。ここでは3つの位置を、動物、乗り物、食べ物とします。数が大きいほど、その言葉はそれに強く関わっています。

例: 作り物の4つのベクトル

言葉動物乗り物食べ物
ねこ0.90.10.1
こねこ0.80.10.2
バス0.10.90.0
おにぎり0.10.00.9

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

コサイン類似度は似ている度合いの点数

2つのベクトルを比べるには、3つの小さな手順を踏みます。内積は、同じ位置の数を掛けて足したものです。長さは、自分自身との内積の平方根です。

コサインは、内積を2つの長さで割ったものです。矢印が同じ向きなら1、直角なら0、反対向きなら0より小さくなります。

例: 2つの小さなベクトル

手順a = [1, 2] と b = [2, 1] の計算結果
内積1 x 2 + 2 x 14
a の長さ(1 x 1 + 2 x 2) の平方根2.24
b の長さ(2 x 2 + 1 x 1) の平方根2.24
コサイン4 を (2.24 x 2.24) で割る0.8

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

計算をループで書く

次のスクリプトは、4つのベクトルを持ち、3つの手順を小さな関数にします。すべての組のコサインを表示します。

数えるベクトルも作ります。決めた漢字を並べ、それぞれが文に何回出るかを数えます。日本語は言葉の間に空白がないので、1文字ずつ数えます。

ベクトルのスクリプトを書く(1)

コマンド
docker exec -w /home/node/project agent sh -c "printf '%s\n' '// 小さな作り物のベクトル: [動物, 乗り物, 食べ物]。本物の埋め込みは数百個の数です。' 'const vectors = {' '  \"ねこ\": [0.9, 0.1, 0.1],' '  \"こねこ\": [0.8, 0.1, 0.2],' '  \"バス\": [0.1, 0.9, 0.0],' '  \"おにぎり\": [0.1, 0.0, 0.9],' '};' 'function dot(a, b) {' '  let total = 0;' '  for (let i = 0; i < a.length; i++) total = total + a[i] * b[i];' '  return total;' '}' 'function length(a) { return Math.sqrt(dot(a, a)); }' 'function cosine(a, b) { return dot(a, b) / (length(a) * length(b)); }' > vec.js"

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

ベクトルのスクリプトを書く(2)

コマンド
docker exec -w /home/node/project agent sh -c "printf '%s\n' 'const names = Object.keys(vectors);' 'for (let i = 0; i < names.length; i++) {' '  for (let j = i + 1; j < names.length; j++) {' '    const score = cosine(vectors[names[i]], vectors[names[j]]);' '    console.log(names[i] + \" と \" + names[j] + \": \" + score.toFixed(2));' '  }' '}' '// 数えるベクトル: 決めた漢字が、文の中に何回出るか。' 'const letters = [\"開\", \"閉\", \"本\", \"遅\"];' 'function counts(sentence) {' '  return letters.map(function (letter) { return sentence.split(letter).length - 1; });' '}' >> vec.js"

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

ベクトルのスクリプトを書く(3)

コマンド
docker exec -w /home/node/project agent sh -c "printf '%s\n' 'const one = counts(\"夜は遅くまで開いています。開館は朝9時です。\");' 'const two = counts(\"本は遅れずに返します。閉館は夜8時です。\");' 'console.log(\"数えた結果:\", one.join(\" \"), \"と\", two.join(\" \"));' 'console.log(\"数えた結果のコサイン:\", cosine(one, two).toFixed(2));' >> vec.js"

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

実行して点数を読む

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

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

表示される主な行

行意味
ねこ と こねこ: 0.99とてもよく似ている
ねこ と バス: 0.22あまり似ていない
バス と おにぎり: 0.01共通点がほとんどない
数えた結果のコサイン: 0.262つの文は、遅の字だけを共有している

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

よくある間違い

注意

コサインが0.9なら「90%同じ」だと考える人が多くいます。そうではありません。点数は順位を付けるためのものです。0.9は0.5より近い、というだけで、真実の割合ではありません。

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

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