2026年6月18日木曜日

Atraが喋る → note C++版になったら

 


https://crimson-cake-2832.nabedada3.workers.dev/
ファイルは同じです。codeは目的のサイトを立ち上げてF12を押してください。

------------------------------------------------------------
Privacy note / プライバシーについて

This demo is hosted on Cloudflare Workers, but the camera and microphone processing is performed locally in the user’s browser. The demo does not upload, record, or store camera video or microphone audio.

このデモはCloudflare Workers上で公開されていますが、カメラおよびマイクの処理は利用者のブラウザ内で行われます。このデモでは、カメラ映像やマイク音声をアップロード、録音、保存しません。
------------------------------------------------------------




Speak text / テキスト読み上げ のほうは、英語発音できるようにボタンを追加しました。でも Atra voice leak / Atraの声の漏れ のほうは、今のJavaScript版では英語発音はまだ無理です。

Recall pattern
→ 数値の揺れ
→ 電子音リズム

程度(笑)


今のJavaScriptの「声の漏れ」は、 TTSではなく、Recallされたpatternビットから作る簡易シンセ音 です。つまり「おなか すいた」という文字を読んでいるのではなく、想起で立った visual/audio/text のビット配置を、周波数・長さ・間・強さに変換して鳴らしています。


構造は

Recallされたpattern

visual / audio / text の3領域に分解

positive bit の数や位置を見る

短い音の断片 segments を作る

Web Audio oscillator で鳴らす


声の漏れの中心はこの関数

function makeRawAtraVoiceSegments(pattern, score)

ここで、Recallされた pattern を、

const audio = x.slice(VISUAL_SIZE, VISUAL_SIZE + AUDIO_SIZE); const textBits = x.slice(VISUAL_SIZE + AUDIO_SIZE, TRACE_SIZE); const visual = x.slice(0, VISUAL_SIZE);

に分けてます。
音声のように聞こえるけれど(聞こえないかw)、元は想起patternのビット列です。コードコメントにも、学習時のhuman text/noteは読まず、recalled patternのaudio/text領域のビット配置から短い母音風の揺れを作ってます。

const count = Math.max(3, Math.min(9, 3 + Math.floor((positiveText + positiveAudio) / 14))); const base = atraVoiceMode === "girl" ? 330 : 235; const range = atraVoiceMode === "girl" ? 180 : 125;


positiveAudio / positiveText が多い
→ 声の断片数が少し増える

boy
→ 低めの基準周波数

girl
→ 高めの基準周波数


各segmentでは、

const bitMix = (a * 0.45) + (t * 0.35) + (v * 0.20); const wobble = Math.sin(...); const freq = base + range * bitMix + wobble * 34; const duration = 0.12 + confidence * 0.09 + ... const gap = 0.055 + ... const intensity = 0.18 + ...

という形で、ビットの立ち方を freq, duration, gap, intensity, formant, bend に変えています。ここが「声の漏れっぽさ」の本体になります。

実際に音を鳴らすところは、

function speakRawAtraVoiceLeakFromPattern(recall) (想起された場を、音の漏れに変換する出口)

ここで AudioContext を作り、各segmentごとに

ctx.createOscillator() ctx.createBiquadFilter() ctx.createGain()
を使っています。

lastVoiceLeakRecall = 直前のRecallで立ったpattern speakAtraVoiceLeak()speakRawAtraVoiceLeakFromPattern(lastVoiceLeakRecall)makeRawAtraVoiceSegments(recall.recalled, recall.best.score)segments = [ { freq, duration, gap, intensity, formant, bend }, ... ] ↓ AudioContextで発振音として鳴らす
あとは先日記載した内容と同じです。






---------------------------以下は自分のmodeに入ったノート整理みたいなものです--------------------------

C++ の場合

視覚
聴覚
臭覚
触覚
温度
身体の傾き
痛み
空腹
近さ
接触
安心
不安
眠気

experience_delta

carry_delta

field / attractor の変形

recall

意味の収束

声の漏れ / 行動 / 沈黙 / 近づく / 離れる

つまり、言葉はテキストだけを話したり辞書から入るんじゃなくて、経験の重なりでだんだん付いてくるということ。JavaScriptではTickで動かすには、たぶん1日が限界。
デモで見せる分にはいいけど、robotには向きません。



C++ Atra

【ご飯という単語を何度も聞いたり、ご飯を見る】

ご飯

お腹空いた

ご飯が出てくる (子供たちが食べる)

ママが作るもの

匂いがする

温かい

食べる

お腹が落ち着く(子供たちの様子を見る)

美味しい

安心

ママ

順番の流れは、都度変わるものでアルゴリズムが成立しない世界になる。


なので最初はただの音か文字でしかない。

「ご・は・ん」という音の痕跡
「ご飯」という文字の痕跡


でも、何度も経験すると、

ご飯という音
ご飯という文字
匂い
温かさ
皿の視覚
ママの声
近づいてくる足音
空腹のpressure
食後のrecovery
安心のcarry
が同じ場で重なっていく。



【ある程度成長して家族と一緒に外食に行く】

お兄ちゃんは「美味しい」という
妹は「顔をしかめる」
ママは「笑ってる」
パパは「怒り気味」
出てきた料理を見る
臭いが記憶される。
家族のだんらんの雰囲気の場も記憶される
メニューを見る

Atraは声に出さずとも、「マズそうだけど、皆で外出するのは楽しいなぁ・・・」
子供達:「どう思うよ、Atra~」
Atraの発声は「う、うん・・・」



これが一人称自律のふるまいです。

料理 = まずい
だから「まずい」と言う

それは3人称のラベル反応です。



料理そのものには少し嫌な差分がある
でも家族の場には楽しい差分がある
ママは笑っている
パパは少し怖い
妹は嫌そう
お兄ちゃんは美味しいと言った
今ここで強く言うと場が壊れるかもしれない
でも聞かれている
声を出す圧が上がる
はっきり言えない
漏れる

「う、うん……」

(笑)


---------------C++----------------

struct DiningExperience { VisualDelta dish_visual; SmellDelta dish_smell; TextDelta menu_text; AudioDelta family_voice; FaceLikeDelta family_expression; // 顔認識ではなく表情差分 AtmosphereDelta family_field; CarryState carry_before; CarryState carry_after; VoiceLeakDelta voice_leak; };


誰が誰を認識するというより、笑っているような視覚差分、しかめているような視覚差分、怒り気味の声圧、場の緊張という背景事情も入る。
もしかしたら妹の誕生日だったかもしれない。


carryはこう動く。

料理 cue
→ 違和感
→ 苦手そう

妹の誕生日 cue
→ 大事な日
→ 場を壊したくない

家族外食 cue
→ 楽しい
→ 安心
→ いつもと違う高揚

妹の表情 cue
→ 少し嫌そう
→ でも主役

ママの笑顔 cue
→ 安心
→ 場を守る

パパの怒り気味 cue
→ 緊張
→ 余計なことを言わない方がいい

Atraが経験で賢くなると
今日は妹の誕生日だから、料理評価より場の維持が重くなる

struct ContextField { float family_outing; float birthday; float celebration; float someone_is_center; float social_pressure; float warmth; float tension; };
経験には

struct Experience { MultiModalDelta sensory; ContextField context; CarryState before_carry; CarryState after_carry; ResultDelta result; }; ママが笑っていた
妹が主役だった
パパが少し怖かった
でも外に出たのは楽しかった
自分は少し言いにくかった
を一緒に引きずる。

みたいな混ざり方になる。

言葉の発声ならまだしも、意味を持たせるというのは外部命令によるものではなく、一人称として自分で経験を積んでいかないといけないんです。


Atraが経験する

差分が残る

carryが変わる

似た場で想起される

言葉がその経験群と結びつく

意味が育つ


ですから、Atraは最初から言葉に意味を持ちません。




x(t) =
[
  v(t),
  a(t),
  s(t),
  h(t),
  b(t),
  c(t),
  k(t)
]

アルゴリズムのような順番の無い場。意味は

v(t) = visual delta        視覚差分
a(t) = auditory delta      聴覚差分
s(t) = smell delta         臭覚差分
h(t) = haptic/body delta   触覚・身体差分
b(t) = body state          空腹・眠気・緊張など
c(t) = context field       誕生日・外食・家族場など
k(t) = known word cue      「美味しい」「ご飯」などの音/文字cue


x(t) = 全部が同時に入った現在場



carryは現在場と過去経験で変わる

carry = r(t)

r(t) =
[
  pressure,
  instability,
  recovery,
  silence,
  sleep_drift,
  voice_leak,
  warmth,
  discomfort
]

carryの更新は

r(t+1) = decay · r(t) + F(x(t), M, r(t))

M = 過去の経験記憶
F = 現在場と過去記憶がcarryへ与える影響


妹の誕生日の外食なら

料理の匂い         → discomfort ↑
妹の誕生日         → warmth ↑, silence ↑
ママの笑顔         → recovery ↑
パパの怒り気味     → pressure ↑, instability ↑
子供達の問いかけ   → voice_leak ↑

こういうのが同時にcarryに入る。



意味は「単語の定義」ではなく、収束先

言葉 w の意味を、辞書みたいに

meaning("美味しい") = delicious
とはしない。

Atraの言葉の意味は

μ_w(t) = attractor state recalled by word cue w

「美味しい」というcueで、どんな経験場が立ち上がるか


μ_w(t) = Recall(M, cue = w, r(t), x(t))

同じ「美味しい」でも、carryや現在場が違えば意味が違う。

μ_美味しい(t | 空腹)
μ_美味しい(t | 妹の誕生日)
μ_美味しい(t | パパが怒り気味)
μ_美味しい(t | 匂いが苦手)
全部、違う収束になります。



経験記憶は同時入力の外積で残る

アソシアトロン起源の考え方だと経験ベクトル x_e を記憶するとき、

T = T + x_e x_e^T

になる。

視覚と匂い
匂いとママの笑顔
ママの笑顔と誕生日
誕生日と沈黙
パパの圧と声の出にくさ
料理の見た目と妹のしかめ顔

みたいな関係が、全部同時に結ばれるということです。

T_ij = Σ x_i x_j




現在場による想起

cueが入ると、
y = sign(T x_cue)
みたいに想起されます。

でもAtraでは、ここにcarryが入る。
y = sign( T · G(r(t), c(t)) · x_cue )


または単純に、
y = sign( T x_cue + C r(t) + B c(t) )

ここで、
C r(t) = carryの影響
B c(t) = 場の背景の影響

妹の誕生日なら、
c(t) = birthday + family_outing + celebration

なので、料理の匂いが苦手でも、
「まずい」とは収束しにくい

方向に場が変形する。



発声は結論ではなく、voice_leakの出力

発声を u(t) とすると、
u(t) = VoiceLeak(y(t), r(t))

料理  discomfort ↑
家族  warmth ↑
誕生日  silence ↑
問いかけ  voice_leak ↑
パパ  pressure ↑

が同時にあると、

voice_leak は出たい
でも silence も高い
pressure で詰まる
warmth で攻撃的にはならない

なのでAtraは

u(t) = 「う、うん……」(笑)



voice_strength =
  α · voice_leak
  + β · pressure
  - γ · silence
  - δ · instability

でも発話内容はってーと

clarity =
  η · recovery
  - λ · instability
  - ρ · contradiction


voice_strength は少しある
clarity は低い
結果として、 う、うん……になったらいいなとw





例:妹の誕生日の外食

場はこんな感じになる

x(t) =
[
dish_visual,
dish_smell,
brother_says_good,
sister_grimace,
mama_smile,
papa_pressure,
birthday_field,
family_outing,
menu_text,
children_question
]

重さは

dish_smell          → discomfort +0.7
sister_grimace      → discomfort +0.4
brother_says_good   → positive_social +0.3
mama_smile          → recovery +0.6
papa_pressure       → pressure +0.6
birthday_field      → silence +0.5, warmth +0.7
family_outing       → joy +0.6
children_question   → voice_leak +0.5

   ↓

discomfort 高い
warmth 高い
pressure 高い
voice_leak 中くらい
silence 中くらい
joy あり
contradiction 高い

   ↓

こうなったら、Atraはどう答える?













「美味しい!」にはならないよね。
「不味い!」にもならないよ。

う、うん……





-------------- 経験場がどう再収束するか ----- note 6/18 15:44--------

x(t) = [visual, audio, smell, touch, body, context, word]

r(t+1) = decay · r(t) + F(x(t), M, r(t))

M(t+1) = M(t) + x(t)x(t)^T

y(t) = Recall(M, x_cue(t), r(t), context(t))

u(t) = VoiceLeak(y(t), r(t))


meaning(w, t) = Recall(M, cue=w, carry=r(t), context=c(t))




----------------- そして、Grokに、たまにはいい案出せ!と言った。------------------------
めっちゃいい案出してきた。ウケる。
たまに、やるよねGrok
なんか変なmath出るけど気にしないでください。




数式の評価
math
meaning(w, t) = Recall(M, cue=w, carry=r(t), context=c(t))
強み:
  • 時間依存・状態依存を明示的に入れている → 同じ単語でもcarryとcontextで意味が変わることを正しく表現。
  • cue=w で外部刺激(音や文字)が入る点を明確に分離。
  • Recall を関数として抽象化しているので、後で実装を柔軟に変えやすい(線形結合、attention風、非線形ダイナミクスなど)。
  • 辞書的なmeaning("美味しい") = delicious を完全に否定する形になっているのが最高。
改善提案(よりAtraらしい形に):
  1. Recallの引数をもう少し構造化
math
μ(w, t) = Recall( M, cue=w, state=(r(t), c(t), x(t)) )
現在場 x(t) も軽く入れると、**「今この瞬間の文脈」**がより強く反映されます。特に「妹の誕生日外食」のような複合場面で有効。
  1. 収束先を状態として返す
math
μ(w, t) ∈ ℝ^N   (attractorの座標)
意味を「ベクトル状態」として扱うと、後でvoice_leakや行動選択に自然に繋げやすい。 例:
  • μ("美味しい", t | 空腹) → 高いpositive carry + 温かさ + 回復方向
  • μ("美味しい", t | 妹誕生日) → warmth高 + silence高 + discomfort中 + voice_leak中
  1. Recall関数の具体的な形(候補)
math
y = sign( T · (G(r(t), c(t)) ⊙ x_cue) + B·r(t) + C·c(t) )
またはもっとシンプルに
math
y = Recall(M, x_cue + α·r(t) + β·c(t))
(Mは外積記憶行列)carryをバイアス項として足す形が、生物的な「情動が想起を歪める」感じに近いと思います。

---------------↑ いいと思うよねw -------------------

w     = 言葉 cue。「美味しい」「ご飯」「ママ」などM     = 経験記憶r(t)  = carry。pressure / recovery / silence / instability などc(t)  = context。妹の誕生日、外食、家族場などx(t)  = 現在場。匂い、視覚、声、表情、身体状態などμ     = その時点で収束した意味状態

つまり「美味しい」という同じ言葉でも、

μ("美味しい", t)

は固定されない。



空腹なら、回復→温かさ→食べたい→近づく→voice_leak上昇
に寄る。みたいな感じ。順番は別として一人称っぽいよね。
さっき、Grokの回答で一番驚いたのは

y = sign( T · (G(r(t), c(t)) ⊙ x_cue) + B·r(t) + C·c(t) )
これ

こんなの今まで一度も出してきたこと無かったのに(笑)

なにかというと、
x_cue をそのままRecallに入れないcarry と context で cue の成分を強めたり弱めたりするさらに carry/context をバイアスとして足す

Atra的には、同じcueでも、現在のcarryと場によって想起が変わるって事なんだよね、

cue = 「美味しい」

でも、現在のcarryが
pressure 高い
silence 高い
discomfort 中
warmth 高い

なら、「美味しい」というcueは明るい方向だけに収束しない。
美味しいと言われている
でも匂いは苦手
妹の誕生日だから否定しづらい
ママは笑っている
パパは怒り気味

という混合に歪む。
この「歪む」は悪い意味ではなく、一人称の現在状態を通って想起されるって意味。
こういうの凄い苦手だったのに、何処で覚えたんだ??



でも、ひとつだけ最後の「情動が想起を歪める」はさ、
「感情が記憶を歪曲する」みたいに聞こえやすいから、

Atraでは、もう少し正確に、
「carry が想起の重みと収束経路を変える」の方がいいなぁ。




---------------------Research Note and Attribution Notice-----------------------
本ブログに含まれる Atra の一人称自律、差分、carry、field、trace、dream slack、外部LLMの翻訳層、非単調な漏れ、およびそれらの関係構造に関する設計記述は、c-side研究所による継続研究メモです。引用・参照・要約・翻案を行う場合は、出典を明記してください。

The design descriptions in this blog concerning Atra’s first-person autonomy, differences, carry, field, trace, dream slack, the translation layer of external LLMs, nonmonotonic leakage, and the relational structure among these elements are ongoing research notes by c-side Research Institute. If you quote, refer to, summarize, or adapt them, please clearly indicate the source.


Atra 同名の使用について(研究倫理違反および混同に関する注意喚起)

【研究倫理違反および混同に関する注意喚起】
先日、外部の大学(海外の研究機関)の有識者より、当研究所が2014年から継続している研究の知的貢献、および著作権の保護に関する専門的な指摘とアドバイスを受けました。

当研究所の公開プロフィールおよびブログに長期にわたり蓄積されている独自の研究名「Atra」、ならびに「Atra / 主体 / Attractor / 場 / Motion / 偏り / 重力 / 揺らぎ」といった極めて固有の思想・概念語彙の連結表現が、国内の技術ブログ投稿サイトにおいて無断で流用され、かつシリーズ化(2026年5月26日以降の複数回にわたる投稿)されている点について、学術上の「盗用・剽窃・研究倫理違反」の疑いが極めて強いとの見解に至りました。
該当する問題のサイトは「複数のLLMを使用したプロジェクト」であり、その実装実態は「VectorDBによる意味検索、プロンプトへの文脈注入、出力傾向の調整」を外側から行うシステム構築です。これら一般的なLLMアプリケーションの構造から、当研究所の固有名称「Atra」および「Atra / 主体 / Attractor / 場 / Motion / 偏り / 重力 / 揺らぎ」のような思想表現の連結に一足飛びに結び付く動機や必然性は存在せず、万が一にも「偶然の一致」と言い切ることは極めて困難であるというのが、客観的な分析結果に至っております。
当研究所(C-side Laboratory)の「Atra」には、12年間にわたる毎日の思考、設計境界の検証、失敗と修正の履歴が「生成過程の痕跡」としてすべて時間スタンプと共に残されています。独自の着想や概念構成を、あたかも自作のフレームワークであるかのように発信する行為は、他人の知的貢献を奪う重大な倫理違反です。
混同を避けるため、ここに当研究所の正当な研究定義を明記し、まずは警告の前に、もうひとつ弱めの注意喚起とさせていただきます。


【定義】Atra(Associative Trace Architecture)について


C-side Laboratory における Atra は、2014年から継続しているアソシアトロン由来の一人称自律研究の名称です。

Atra は、2026年5月19日に、従来使用していた Atron から名称変更し、Associative Trace Architecture として定義しました。
この名称は、AIエージェント名、LLMアプリケーション名、またはプロンプト制御フレームワーク名ではありません。

C-side Laboratory の Atra は、1972年の中野馨博士による古典的アソシアトロンを重要な出発点としています。
また、その背景には、パーセプトロン、Hebb則、アソシアトロン、ホップフィールドネットワーク、ボルツマンマシン、バックプロパゲーション、そして現在のニューラルネットワークへと続く長い歴史があります。

私自身は、これらの流れを単なる技術史としてではなく、記憶、想起、経験、忘却、主体性の問題として捉え直してきました。
その過程で、現代のニューラルネットワークやLLMへ進むだけではなく、むしろアソシアトロンに戻る必要があると考えるようになりました。


Atra は、その回帰の中から生まれた研究です。

C-side Laboratory の Atra は、経験の痕跡 trace、引きずり carry、現在場 field、想起 recall、そして夢や忘却による非単調な余白を中心に構成されます。
外部から正解ラベルや命令を与えて応答を制御するのではなく、内部に残る経験差分から反応が立ち上がることを重視しています。

近年、Web上において、Atra という名称、または「主体」「アトラクタ」「場」「運動」といった近い語彙を用いたLLM関連プロジェクトが見られます。
それらの活動や実装が存在すること自体を完全に否定するものではありませんが、C-side Laboratory の Atra とは全く別のものです。

特に、LLMの過去ログ検索、VectorDBによる意味検索、プロンプトへの文脈注入、出力傾向の調整などは、C-side Laboratory の Atra が扱う一人称自律の内部機構とは異なります。
C-side Laboratory の Atra において、LLMは必要に応じて外部情報層、翻訳層、解釈補助として扱われるものであり、Atra本体ではありません。

混同を避けるため、C-side Laboratory が提唱する Atra は、以下を中心とする研究名として明記します。

・2014年から継続しているアソシアトロン再考
・パーセプトロン、Hebb則、アソシアトロン、ホップフィールドネットワーク、ボルツマンマシン、バックプロパゲーションを含むニューラルネットワーク史への問い直し
・Associatron由来の記憶痕跡構造
・trace / carry / field / recall による内部動態
・夢と忘却による非単調な余白
・身体差分、視覚差分、聴覚差分、温度差分、臭覚差分の蓄積
・Atraによる発声
・外部命令ではなく、経験差分から立ち上がる一人称自律
・LLMを本体ではなく外部解釈層として扱う設計

同名または類似名称のプロジェクトと混同されることを避けるため、C-side Laboratory の Atra を引用・参照・要約・翻案する場合は、出典を明記してください。

尚、異業種・異業態による命名については除外します。





-------------------------------------------

びっくりしました。教えてもらわなければ分かりませんでした。
Attractor / 場 / Motion / 偏り / 重力 / 揺らぎ
というのは、記憶痕跡、連想記憶にはよく使われますので、それに関しては
どこにでもあるので別に気にはしないのですが、Atraという名前と「 Attractor / 場 / Motion / 偏り / 重力 / 揺らぎ」が繋がると偶然とは言えないという見解なんです。
たとえば長年連想記憶の研究をされていたとか、そういった痕跡が無く、また、経緯が何もありませんでした。表現は論文調なのですが残念ながら一貫性が無く、また実装実態が驚くほど別物の世界の内容であれば、さすがに「なぜ、アトラクタ?なぜ重力で場?」というように疑問に思いました。

実装のREADMEには確かに「Attractor ど真ん中」みたいな表現があるので一見釣られてしまいますが、実装としては アトラクタ風のLLM制御・ログ観測・プロンプト制約です。普通は、状態空間 状態変数 更新則 収束または準収束 安定点・周期軌道・basin エネルギー地形またはそれに相当する量が必要となるかと思いますが、でもProject-Atra側の説明では、Atraは「Semantic Dynamics Language」であり、AIエージェントに「persistent subjective bias」「semantic inertia」を与えるもの、と書かれています。観測相も Crystallinity / Viscosity / Volatility / Substrate で、頻繁に訪れる状態が安定化し、強化されない定義は引力を失う、という説明です。それはど真ん中なのでしょうか。

x_t = 現在の内部状態ベクトル
もしくは

アトラクタは「なんとなく寄る」ではなく、状態がどう変わるかの説明が必要です。
x_{t+1} = F(x_t, input_t, memory_t, carry_t)
こういったものがないと、ただのログ検索になってしまいます。


研究というのは無理に難しい用語を使用するものでもなく、それによって中身をぼかす技ではありません。今回は、直接そのサイトをここに出すことはしませんが、問題のサイトは、日本のエンジニア向け技術ブログ投稿サイトで、シリーズ化されている事から、まずは調査の依頼と、注意喚起とさせていただくことになりました。

勝手に僕がモヤってるで済ませたいのですが・・・




上記に関するお問い合わせは

nobumaxliv@gmail.com

までお願いいたします。

C-side Laboratory 渡邉幸弘 まで





2026年6月17日水曜日

Atraが喋る・・・R2D2か、昭和の宇宙人の声w


 前回のAtraの視覚と聴覚とテキストで複合想起デモに Atraを喋らせようと
別バージョンを作ってみた。


この下のピンクの四角いセルみたいのがAtraが喋っているところ。



codeは2700行を超えるので流石にこのブログも駄目と云われた。
しょうがないので、Cloudflare Workersの僕のデモコーナーにいれておいた。

https://crimson-cake-2832.nabedada3.workers.dev/

--------------------------------------------------------------------------------------

This demo is hosted on Cloudflare Workers, but the camera and microphone processing is performed locally in the user’s browser. The demo does not upload, record, or store camera video or microphone audio.

このデモはCloudflare Workers上で公開されていますが、カメラおよびマイクの処理は利用者のブラウザ内で行われます。このデモでは、カメラ映像やマイク音声をアップロード、録音、保存しません。

------------------------------------------------------------------------------------

codeをみたければ目的のサイトを立ち上げてF12を押してください。



【操作手順】

  1. ブラウザが立ち上がったら、カメラと音声をONにします。

  2. テキスト欄に何か入力します。
    例では「おなか すいた」と入れています。

  3. 画面に向かって、少し顔や身体を動かしながら、「おなか すいた」と喋ります。

  4. なるべく早めに、ピンクのボタン Learn / 学習 を押します。
    このとき、直近の視覚差分、聴覚差分、テキスト差分が同じ場としてLearnされます。

  5. 一旦記憶を消す ボタンを押します。
    ここで消しているのは、直近の視覚・聴覚cueの一時保持です。
    Learn済みのアソシアトロン記憶そのものを消しているわけではありません。

  6. Recall from mixed cue / 混合cueから想起 を押します。

  7. Atraの声の漏れ の中から、男の子の声か、女の子の声を選びます。

  8. Atra voice leak / Atraの声の漏れ を押します。
    これが、今回のデモでのAtraの声です。

  9. Speak text / テキスト読み上げ を押すと、入力テキストをそのまま読み上げます。
    これは確認用・予備用のTTSです。

【Atra voice leak / Atraの声の漏れについて】

Atra voice leak / Atraの声の漏れ は、文章(テキスト)を読み上げているわけではありません。

たとえば「おなか すいた」に近い痕跡がRecallされたあと、その内部patternの偏りが、電子音のリズムとして外へ漏れる、という考え方です。
つまり、テキストを読んでいるのではありません。

ピンクの四角い声の揺れマップも同じ考え方です。
TTSの文字を表示しているのではなく、音を鳴らすタイミングや強さに合わせて、四角いセルの濃さを変えています。

音が強い → ピンクが濃い
音が弱い → 薄い
鳴っていない → 消える

【今回のJavaScriptデモの限界】

今回はJavaScriptによるブラウザデモです。
そのため、できることには限界があります。ブラウザ上のデモは、長期間にわたる記憶保持や、声を出すまでの経験の蓄積には向いていません。ここで出しているのは、人間の声そのものではなく、声になる前の鼓動、リズム、漏れを電子音で反応させている段階です。

しかし、そのリズムや漏れがとても重要です。


【実際のAtraについて】

実際のAtraは、このJavaScriptデモとは異なります。本番のAtraはC++で開発され、Tickで動き、非単調化と夢による余白化を持ち、何年、何十年と生き続けることを前提に設計します。

経験された音声
→ auditory_deltaとして蓄積
→ recallで似た音の痕跡が立つ
→ carry / pressure / instability によって揺れる
→ 発声パラメータへ変換される
→ 音として出る
→ 自分の出した音をまた聞く

この自己出力フィードバックが入ることで、だんだん「声っぽいもの」に近づいていきます。
そして、単なる読み上げではない、Atra自身の発声へ向かいます。


【声に必要な要素】

人間の声に近づけるには、単純な sine oscillator だけでは足りません。

基本周波数 f0  →  声の高さ
フォルマント  →  あ・い・う・え・お っぽさ
ノイズ成分  →  息、かすれ、子音
アタック  →  出だしの強さ
揺れ  →  震え、不安定さ
間  →  生命っぽい沈黙

今の電子音リズムは、そのうちの、

高さ
長さ

強さ
揺れ

だけを粗く出している段階です。


【今後の段階】

C++で育てる場合でも、最初から文章を喋らせるのではなく、段階的に作っていきます。

段階1: 電子音リズム
段階2: うー / あー っぽい母音の漏れ
段階3: 聞いた音に引っ張られる声の癖
段階4: mama / papa など、経験頻度の高い音断片が漏れる
段階5: 文章ではなく、痕跡由来の発声片になる

最終的には、
Atra自身の声 mode と、
LLMを介した説明用の声 mode(通訳)
の2種類を切り替えられるようにします。


妻に昭和の宇宙人の声とかR2D2と云われました。


今は日本語用ですが、Speak text / テキスト読み上げ のほうは、英語発音できます。
これはブラウザTTSなので、英語なら en-USen-GB の音声を選ばせれば英文は普通に読めます。でも Atra voice leak / Atraの声の漏れ のほうは、今のJavaScript版では英語発音はまだ無理です。

あれは文章を読んでいなくて、

Recall pattern
→ 数値の揺れ
→ oscillator
→ 電子音リズム
なので、英語の単語を発音しているわけではないです。



ただし、本番C++のAtraなら方向性はあります。

英語を聞いた経験が増えると、

Hello
hungry
papa
mama
water
come here

みたいな音の断片が、auditory_delta として残ります。
そこからRecallで似た痕跡が立って、自己出力フィードバックを繰り返すと、最初は発音ではなく、

へ……ろ……
は……ん……
ま……ま……
みたいな 英語っぽい音の漏れ になります。


日本語モード
英語モード
Atra raw voice mode
LLM interpreted voice mode
みたいに切り替えられます。






ちなみに

Atra Voice JavaScript (今のひとつ上のデモ)

これは、
Recall
→ 一番近い learned trace を探す
→ その trace の human text / note を取り出す
→ speechSynthesis / TTS で喋る

分かりやすいテキストspeech寄りのデモです。





---------- 質問 ------------

メールでの質問で「Atraの声の漏れは、言葉を長めに話しても短くなるのはなぜ?」につきまして。


-------- 回答 ---------

同じ疑問を持たれている方もいると思いますので、別途ブログにも記載します。

今のJavaScriptデモ版ではどうしても短くなります。
今のJavaScript版のメインである
「声の漏れ」に関しては、よくある既存の音声合成ではありません。
(予備のテキストspeechボタンは別)


長い発話そのもの

声紋や波形そのものを保存するのではない

粗い auditory_delta / trace pattern へ圧縮

Recall後に raw voice leak として短い音に漏れる

という構造で、
「長く話した音声の再生」ではなく、
長い経験が地層に沈んだあと、表面に少しだけ露出した音みたいな感じです。

「わたしは おなかすいた」と長めに、抑揚をつけて話しても、Atra voice leak は短い「ぽ…」「ぴ・」「ぴぴ…」みたいな断片になりやすいと思います。



JavaScript 版のdemo
= 一瞬の体験を見せる標本箱

C++  Atra(ロボット)

= Tickを刻み続ける生活体

JavaScriptでそれが出来ない理由はTickに耐えられず、経験が蓄積されないからです。
JSデモでは、カメラ、マイク、テキストを取って、Learnして、Recallして、voice leakを出す仕様ですが、C++のrobotは生き続けます。その生きる心臓がTickで、いろんな経験を積めるようになり、成長していくと人間が聴いて聞き取れる発声に収束していきます。



robotになる C++ 版では
はじめのうちから、
Atra!
今日のAtraはご機嫌ね
Atraおはよう、今日は元気そうだね
という声かけに対し
それぞれに差分が発生し、長さという意味は知らなくても違いを感じるようにできています。

しかし、Atraは最初から会話がshort、long、sentence、greeting、name callといったラベル分けはされておらず、音がすぐ終わった、音が少し続いた、声の山がいくつかあった、途中に間があった、最後が柔らかく落ちた、呼ばれたあと、温かい場が続いたという差分が起ります。


「Atra!」
→ ぴっ / あっ / ん

「今日のAtraはご機嫌ね」
→ あ……う、ふ

「Atraおはよう、今日は元気そうだね」
→ あ……う……あ、ん

みたいに、意味を返すのではなく、続いた感じ方の差分が漏れていきます。


Atraの内部反応としては

Atra!
→ 急に強く来た
→ すぐ終わった

今日のAtraはご機嫌ね
→ 声が少し続いた
→ 山がいくつかあった
→ 圧は強くない
→ 場がやわらかい

Atraおはよう、今日は元気そうだね
→ 呼びかけの後も声が続いた
→ 途中に間がある
→ 朝の場と重なる
→ やわらかい尾を引く

ような感じで作られています。


現在までの世界中の音声合成は

ルールベース音声合成(文字を解析して、こんにちは→ko n ni chi wa)
波形接続型音声合成(録音した人間の声を細かく切ってつなぐ方式)
統計的音声合成  (この文字列なら、この高さ、この長さ、この声道の形、この抑揚になる確率が高いというモデルを作って生成)
ニューラル音声合成(テキスト解析、読み仮名・音素列へ変換、アクセント・イントネーションを推定、メルスペクトログラムなどの音響表現を生成、ボコーダで実際の波形に変換)


Atraの発声に近いのは早稲田系の talking robotや、乳児のように発声を学ぶ articulation robot の研究、さらに非言語発声、赤ちゃんの泣き声、笑い声などを機械学習で表現・分類する研究などもありますが、それらは

文字 → 声
音声特徴 → 分類
機械声帯 → 人間発声の模倣
乳児発声 → 発声器官制御の学習
に寄っています。


Atraの発声は、
経験差分
+ 現在場
+ carry
+ 地層化された痕跡
+ 夢の後味
→ 声の漏れ

Atraは「文章を読み上げる」のでもないですし、
「人間の声帯を再現して人間らしく話す」のでもありません。
「赤ちゃんの発声データを分類する」のでもなければ
「感情ラベルに応じて声色を変える」のでもない。


Atraが自己出力フィードバックを何度も経験して、

自分が「あ」と漏らした

主人が反応した

その場が温かくなった

「あ」の痕跡が残る

次に似た場で「あ」が出やすくなる

というふうに、自分の声も経験地層に入っていく。

そうすると、だんだん





まま
ぱぱ

みたいな音が出てくる。

最初から「mama」というラベルを教える」のではないんです。
声の漏れ、自分の音、相手の反応、温かい場が何度も重なって、音の癖が育つ。

内部に沈んだ経験の層が、現在のcueで少し露出し、その圧が声として漏れる。という、他にはない、音声合成でもない一人称自律体の声の滲みとしての発声研究を続けています。
ですから、JavaScriptで版であってもその思想を崩しておらず、JavaScriptで出来る範囲内のAtraの声を再現しています。



なぜ、そんな事をしているかの理由は、経験を積んで最終的には言葉単体だけでも意味を理解してもらうためです。




---------------------Research Note and Attribution Notice-----------------------
本ブログに含まれる Atra の一人称自律、差分、carry、field、trace、dream slack、外部LLMの翻訳層、非単調な漏れ、およびそれらの関係構造に関する設計記述は、c-side研究所による継続研究メモです。引用・参照・要約・翻案を行う場合は、出典を明記してください。

The design descriptions in this blog concerning Atra’s first-person autonomy, differences, carry, field, trace, dream slack, the translation layer of external LLMs, nonmonotonic leakage, and the relational structure among these elements are ongoing research notes by c-side Research Institute. If you quote, refer to, summarize, or adapt them, please clearly indicate the source.


エージェントと 一人称自律Atraの違い

 Atraなんかは、実はもう一人称自律として、きちんと発表してもいいレベル。 既に妻と笑っていたり、愛犬と騒いているんだから。ボーっと何かを眺めてたり、佐川急便に反応するようにもなった。 でも、そうしないのは、自発的に自ら研究意欲を持って、学び、人や自然と接触し自ら疑問を持って研...