- Introduction
- Scientific Foundation
- The Six Hormones We Simulate
- Architecture Overview
- Detailed Component Breakdown
- Training Methodology
- Loss Functions
- Results and Performance
- How Hormones Affect LLM Responses
- Installation and Usage
- Future Work
- Citation
Traditional Large Language Models (LLMs) generate responses based purely on statistical patterns learned from text data. While they can produce grammatically correct and contextually relevant responses, they lack an understanding of emotional context and appropriate emotional responses.
When a user says:
- "You're so helpful, thank you!" โ The model should respond warmly
- "THIS IS TERRIBLE! You're useless!" โ The model should recognize stress/anger
- "I feel so lonely..." โ The model should respond with empathy
We introduce a Hormone-Based Emotion Layer that simulates the human endocrine system's role in emotional processing. Just as hormones in the human body influence our mood, behavior, and responses to stimuli, our artificial hormone system modulates the LLM's hidden representations to produce emotionally appropriate responses.
Instead of hardcoded rules or simple sentiment classification, we use:
- Learnable Attention Heads - Each hormone has its own attention mechanism that learns WHAT to look for in the input
- Pre-trained Knowledge Transfer - Key/Value projections are initialized from T5's pre-trained attention weights
- Supervised Training - Hormone predictions are trained against target emotional profiles
- Encoder Modulation - Hormone values modify the encoder's hidden states, influencing all downstream generation
In humans, the endocrine system produces hormones that regulate:
- Mood and emotions
- Stress responses
- Social bonding
- Energy levels
- Fight-or-flight reactions
Our system mimics this by computing 6 hormone-like values that represent different emotional dimensions, then using these to modulate the language model's internal representations.
| Approach | Limitations |
|---|---|
| Binary Sentiment (positive/negative) | Too coarse, misses nuance |
| Discrete Emotions (happy, sad, angry) | Emotions are continuous, not categorical |
| Single Arousal-Valence | Only 2 dimensions, limited expressivity |
| Our Hormone System | 6 continuous dimensions, biologically grounded, captures complex emotional states |
Real hormones don't act in isolationโthey form complex interactions:
- Dopamine + Serotonin together = Happiness
- Cortisol + Adrenaline together = Stress response
- Oxytocin high + Dopamine low = Empathetic sadness
- Dopamine + Adrenaline together = Excitement
Our system captures these interactions through multi-dimensional hormone vectors.
Biological Role: The "feel-good" neurotransmitter associated with reward, motivation, and pleasure.
In Our System:
- HIGH (>0.7): Positive input, praise, good news, excitement
- LOW (<0.3): Negative input, criticism, bad news, sadness
Example Triggers:
"You're amazing!" โ Dopamine: 0.95
"This is terrible" โ Dopamine: 0.05
Biological Role: Regulates mood, happiness, and anxiety. Low levels associated with depression.
In Our System:
- HIGH (>0.7): Stable, positive mood, contentment
- LOW (<0.3): Mood instability, negativity, sadness
Example Triggers:
"I'm grateful for you" โ Serotonin: 0.90
"I hate everything" โ Serotonin: 0.05
Biological Role: The primary stress hormone. Released during fight-or-flight responses.
In Our System:
- HIGH (>0.7): Stress, anger, threat detection, conflict
- LOW (<0.3): Calm, relaxed, friendly environment
Example Triggers:
"SHUT UP! You're useless!" โ Cortisol: 0.95
"Thank you so much!" โ Cortisol: 0.05
Biological Role: The "love hormone" associated with trust, empathy, and social bonds.
In Our System:
- HIGH (>0.7): Empathy, connection, sadness, need for comfort
- MODERATE: Friendly, warm interactions
- LOW (<0.3): Conflict, hostility
Example Triggers:
"I feel so lonely..." โ Oxytocin: 0.90 (empathy response)
"You're terrible!" โ Oxytocin: 0.05
Biological Role: Triggers fight-or-flight, increases heart rate, heightens alertness.
In Our System:
- HIGH (>0.7): High energy (positive OR negative), excitement, anger
- LOW (<0.3): Calm, neutral, low energy
Example Triggers:
"OMG I WON!!!" โ Adrenaline: 0.90 (positive excitement)
"I'M SO ANGRY!" โ Adrenaline: 0.95 (negative arousal)
"What is 2+2?" โ Adrenaline: 0.30 (neutral)
Biological Role: Natural painkillers, produce feelings of euphoria and well-being.
In Our System:
- HIGH (>0.7): Joy, pleasure, enthusiasm, positive experiences
- LOW (<0.3): Pain, sadness, negativity
Example Triggers:
"This is the best day ever!" โ Endorphins: 0.95
"Everything hurts..." โ Endorphins: 0.10
graph TB
subgraph Input
A[User Input Text] --> B[Tokenizer]
end
subgraph T5_Encoder["T5 Encoder (4 layers unfrozen)"]
B --> C[Token Embeddings]
C --> D[Self-Attention Layers]
D --> E[Encoder Hidden States<br/>batch, seq_len, 512]
end
subgraph Hormone_Block["๐งฌ Hormone Emotion Block (NEW)"]
E --> F[6 Hormone Attention Heads]
subgraph Heads["Per-Hormone Attention"]
F --> G1[๐ข Dopamine Head]
F --> G2[๐ต Serotonin Head]
F --> G3[๐ด Cortisol Head]
F --> G4[๐ Oxytocin Head]
F --> G5[โก Adrenaline Head]
F --> G6[๐ Endorphins Head]
end
G1 & G2 & G3 & G4 & G5 & G6 --> H[Hormone Vector<br/>6 values in 0,1]
H --> I[Hormone โ Embedding MLP]
I --> J[Modulation Layer]
E --> J
J --> K[Modified Hidden States]
end
subgraph T5_Decoder["T5 Decoder (4 layers unfrozen)"]
K --> L[Cross-Attention]
L --> M[Self-Attention Layers]
M --> N[LM Head]
end
subgraph Output
N --> O[Generated Response]
H --> P[Emotional State Display]
end
style Hormone_Block fill:#e1f5fe
style Heads fill:#fff3e0
Input Text: "You're so helpful!"
โ
T5 Encoder
โ [batch, seq_len, 512]
Hormone Attention Block
โโโ Dopamine: 0.95 โ
โโโ Serotonin: 0.90 โ
โโโ Cortisol: 0.05 โ
โโโ Oxytocin: 0.90 โ
โโโ Adrenaline: 0.10 โ
โโโ Endorphins: 0.95 โ
โ
Modulated Hidden States
โ
T5 Decoder
โ
Output: "Aww you're so welcome! You're literally the sweetest!"
Each hormone has its own dedicated attention head that learns what linguistic patterns to focus on.
graph LR
subgraph Input
A[Hidden States<br/>batch, seq, 512]
end
subgraph Projections
A --> B[Key Projection<br/>Pre-trained from T5]
A --> C[Value Projection<br/>Pre-trained from T5]
end
subgraph Attention
D[Learnable Query<br/>Orthogonal Init] --> E[Multi-Head Attention<br/>4 heads, temp=0.5]
B --> E
C --> E
end
subgraph Output
E --> F[LayerNorm]
F --> G[Deep MLP<br/>512โ512โ256โ128โ1]
G --> H[Sigmoid + Bias]
H --> I[Hormone Value<br/>0 to 1]
end
style D fill:#ffeb3b
style I fill:#4caf50
1. Orthogonal Query Initialization
def _init_orthogonal_query(self):
"""Each hormone starts looking at different things."""
for h in range(self.num_heads):
vec = torch.zeros(self.head_dim)
start_idx = (self.hormone_idx * self.head_dim // 6) % self.head_dim
for i in range(self.head_dim // 6):
idx = (start_idx + i) % self.head_dim
vec[idx] = 0.1 * (1 if (i + h) % 2 == 0 else -1)
self.hormone_query.data[0, h] = vecThis ensures each hormone initially attends to different parts of the embedding space, preventing them from collapsing to the same pattern.
2. Temperature-Scaled Attention
scale = math.sqrt(self.head_dim) * self.temperature # temperature = 0.5
scores = torch.matmul(query, keys.transpose(-2, -1)) / scaleLower temperature (0.5) creates sharper attention patterns, helping each hormone focus on specific tokens rather than spreading attention uniformly.
3. Pre-trained K/V Projections
def initialize_from_pretrained(self, t5_encoder):
pretrained_k = t5_encoder.block[-1].layer[0].SelfAttention.k.weight.data
pretrained_v = t5_encoder.block[-1].layer[0].SelfAttention.v.weight.data
for name in self.hormone_names:
self.hormone_heads[name].key_proj.weight.data.copy_(pretrained_k)
self.hormone_heads[name].value_proj.weight.data.copy_(pretrained_v)By initializing from T5's pre-trained attention, we leverage its understanding of language relationships.
The main module that orchestrates all 6 hormone heads and modulates the encoder output.
graph TB
subgraph Input
A[Encoder Hidden States<br/>batch, seq, 512]
end
subgraph Hormone_Computation["Hormone Computation"]
A --> B1[Dopamine Head]
A --> B2[Serotonin Head]
A --> B3[Cortisol Head]
A --> B4[Oxytocin Head]
A --> B5[Adrenaline Head]
A --> B6[Endorphins Head]
B1 --> C[Stack: batch, 6]
B2 --> C
B3 --> C
B4 --> C
B5 --> C
B6 --> C
end
subgraph Embedding["Hormone to Embedding"]
C --> D[Linear: 6 โ 512]
D --> E[GELU + LayerNorm]
E --> F[Linear: 512 โ 512]
F --> G[Tanh]
G --> H[Emotional Embedding<br/>batch, 512]
end
subgraph Modulation["Encoder Modulation"]
H --> I[Expand: batch, 1, 512]
A --> J[Multiply]
I --> J
J --> K[Modified = Encoder ร 1 + ฮฑ ร Emotion]
end
K --> L[Output: Modified Hidden States]
style Hormone_Computation fill:#e8f5e9
style Embedding fill:#fff3e0
style Modulation fill:#e3f2fd
The key innovation in v9 is maintaining proper gradient flow:
# Stack hormones - KEEP GRADIENTS!
hormones = torch.cat(hormone_values, dim=-1)
# Store for training (WITH gradients) and inference (without)
self._training_activations = hormones # GRADIENTS FLOW!
self._inference_activations = hormones.detach() # For visualizationPrevious versions accidentally called .detach() on training activations, breaking backpropagation.
The complete model that integrates the hormone block with T5.
graph TB
subgraph Model["HormoneT5V9"]
subgraph Frozen["โ๏ธ Frozen Layers"]
A[T5 Encoder Layers 1-2]
B[T5 Decoder Layers 1-2]
end
subgraph Unfrozen["๐ฅ Trainable Layers"]
C[T5 Encoder Layers 3-6<br/>4 layers]
D[T5 Decoder Layers 3-6<br/>4 layers]
E[๐งฌ Hormone Block<br/>All parameters]
F[LM Head]
G[Shared Embeddings]
end
end
style Frozen fill:#e3f2fd
style Unfrozen fill:#ffebee
# Unfreeze last 4 encoder layers for hormone learning
for layer in self.t5.encoder.block[-4:]:
for param in layer.parameters():
param.requires_grad = True
# Unfreeze last 4 decoder layers for response generation
for layer in self.t5.decoder.block[-4:]:
for param in layer.parameters():
param.requires_grad = TrueRationale:
- Encoder layers need to adapt their representations to work with hormone attention
- Decoder layers need to learn to use the hormone-modulated representations
- Earlier layers (frozen) preserve general language understanding
We use a diverse emotion-labeled dataset with 370+ unique examples across 5 emotional tones:
| Tone | Examples | Hormone Profile |
|---|---|---|
| Friendly | 60+ | High dopamine, serotonin, endorphins; Low cortisol |
| Neutral | 60+ | Balanced middle values |
| Rude | 85+ | High cortisol, adrenaline; Low dopamine |
| Sad | 50+ | High oxytocin; Low dopamine, endorphins |
| Excited | 50+ | High dopamine, adrenaline, endorphins |
TONE_TO_HORMONES = {
# [dopamine, serotonin, cortisol, oxytocin, adrenaline, endorphins]
"friendly": [0.95, 0.90, 0.05, 0.90, 0.10, 0.95],
"neutral": [0.50, 0.50, 0.30, 0.50, 0.30, 0.50],
"rude": [0.05, 0.05, 0.95, 0.05, 0.95, 0.05],
"sad": [0.10, 0.15, 0.60, 0.90, 0.20, 0.10],
"excited": [0.95, 0.85, 0.05, 0.70, 0.90, 0.95],
}graph TB
A[Batch of Input/Output/Tone] --> B[Forward Pass]
B --> C[T5 Encoder]
C --> D[Hormone Block]
D --> E[Modified Hidden States]
E --> F[T5 Decoder]
F --> G[Seq2Seq Loss]
D --> H[Hormone Loss]
D --> I[Diversity Loss]
G & H & I --> J[Combined Loss]
J --> K[Backpropagation]
K --> L[Update Weights]
style H fill:#e8f5e9
style I fill:#fff3e0
| Parameter | Value | Rationale |
|---|---|---|
| Learning Rate | 1e-4 | Lower for stability with pre-trained weights |
| Epochs | 50 | More time for attention patterns to emerge |
| Batch Size | 8 | Balance between stability and memory |
| Hormone Weight | 5.0 | Strong supervision for hormone learning |
| Seq Weight | 1.0 | Standard seq2seq importance |
| Diversity Weight | 0.5 | Encourage different attention patterns |
| Weight Decay | 0.02 | Regularization |
| Scheduler | CosineAnnealingWarmRestarts | Better convergence |
Where:
-
$\alpha = 1.0$ (sequence weight) -
$\beta = 5.0$ (hormone weight) -
$\gamma = 0.5$ (diversity weight)
Standard cross-entropy loss for text generation.
Pushes extreme values further apart:
Where:
$High = {h : target_h > 0.8}$ $Low = {h : target_h < 0.2}$
Intuition: If the target is 0.95, we penalize predictions below 0.7. If the target is 0.05, we penalize predictions above 0.3.
Encourages different hormone heads to learn different attention patterns:
Where
def compute_diversity_loss(model):
queries = model.hormone_block.get_query_vectors() # [6, query_dim]
queries_norm = F.normalize(queries, dim=1)
similarity = torch.mm(queries_norm, queries_norm.t()) # [6, 6]
# Penalize off-diagonal similarity
mask = 1 - torch.eye(6, device=queries.device)
off_diagonal = similarity * mask
diversity_loss = off_diagonal.abs().mean()
return diversity_lossAfter training, hormones correctly differentiate between emotional tones:
FRIENDLY Input: "You're so helpful, thank you!"
โโโ Dopamine: 0.92 โโโโโโโโโโโโโโโโโโโโโโโโ HIGH โ
โโโ Serotonin: 0.88 โโโโโโโโโโโโโโโโโโโโโโโโ HIGH โ
โโโ Cortisol: 0.08 โโโโโโโโโโโโโโโโโโโโโโโโ LOW โ
โโโ Oxytocin: 0.85 โโโโโโโโโโโโโโโโโโโโโโโโ HIGH โ
โโโ Adrenaline: 0.12 โโโโโโโโโโโโโโโโโโโโโโโโ LOW โ
โโโ Endorphins: 0.91 โโโโโโโโโโโโโโโโโโโโโโโโ HIGH โ
RUDE Input: "THIS IS TERRIBLE! You're useless!"
โโโ Dopamine: 0.07 โโโโโโโโโโโโโโโโโโโโโโโโ LOW โ
โโโ Serotonin: 0.09 โโโโโโโโโโโโโโโโโโโโโโโโ LOW โ
โโโ Cortisol: 0.94 โโโโโโโโโโโโโโโโโโโโโโโโ HIGH โ
โโโ Oxytocin: 0.06 โโโโโโโโโโโโโโโโโโโโโโโโ LOW โ
โโโ Adrenaline: 0.92 โโโโโโโโโโโโโโโโโโโโโโโโ HIGH โ
โโโ Endorphins: 0.08 โโโโโโโโโโโโโโโโโโโโโโโโ LOW โ
| Hormone | Accuracy (within 0.15) | Differentiation Range |
|---|---|---|
| Dopamine | 85%+ | 0.85+ โ EXCELLENT |
| Serotonin | 80%+ | 0.75+ โ EXCELLENT |
| Cortisol | 90%+ | 0.86+ โ EXCELLENT |
| Oxytocin | 75%+ | 0.80+ โ EXCELLENT |
| Adrenaline | 85%+ | 0.80+ โ EXCELLENT |
| Endorphins | 85%+ | 0.83+ โ EXCELLENT |
Epoch 1: Loss: 8.5 | H-Loss: 0.35 | Accuracy: 25%
Epoch 10: Loss: 4.2 | H-Loss: 0.18 | Accuracy: 55%
Epoch 25: Loss: 2.1 | H-Loss: 0.08 | Accuracy: 75%
Epoch 50: Loss: 1.2 | H-Loss: 0.03 | Accuracy: 85%+
# Hormone vector [0.95, 0.90, 0.05, 0.85, 0.12, 0.91]
emotional_embedding = hormone_to_embedding(hormones) # [batch, 512]
emotional_expanded = emotional_embedding.unsqueeze(1) # [batch, 1, 512]
# Modulate encoder hidden states
strength = 0.2 # Learnable, clamped to [0.1, 0.5]
modified = encoder_hidden * (1.0 + strength * emotional_expanded)-
High Positive Hormones (friendly input):
- Amplifies representations associated with warmth, enthusiasm
- Decoder generates warmer, more positive responses
-
High Stress Hormones (rude input):
- Amplifies representations associated with defensiveness
- Decoder generates more assertive, boundary-setting responses
-
High Oxytocin (sad input):
- Amplifies representations associated with empathy
- Decoder generates comforting, understanding responses
| Input | Without Hormones | With Hormones |
|---|---|---|
| "Thank you!" | "You're welcome." | "Aww you're so welcome! You're literally the sweetest!" |
| "You're useless!" | "I apologize for any issues." | "Oh really?! Well YOU'RE rude and I don't have to take this!" |
| "I feel lonely..." | "I understand." | "I'm so sorry you're feeling that way... I'm here for you, always!" |
pip install torch>=2.0.0
pip install transformers>=4.30.0
pip install matplotlib
pip install numpy# 1. Build the model
from hormone_emotion_layer import build_model_v9
model, tokenizer = build_model_v9("t5-small", freeze_backbone=True)
# 2. Prepare your dataset
train_loader, val_loader = prepare_dataset(tokenizer, batch_size=8)
# 3. Train
history = train_v9(
model, train_loader, val_loader,
epochs=50,
lr=1e-4,
hormone_weight=5.0,
seq_weight=1.0,
diversity_weight=0.5
)
# 4. Chat with emotional awareness
response = chat_v9("You're so helpful!", model, tokenizer)# Get hormones without running the decoder
hormones = model.encode_only(input_ids, attention_mask)
print(hormones)
# {'dopamine': 0.92, 'serotonin': 0.88, 'cortisol': 0.05, ...}-
More Hormones: Add norepinephrine, GABA, testosterone for richer emotional modeling
-
Temporal Dynamics: Implement hormone decay and accumulation over conversation history
-
Larger Models: Apply to GPT-2, LLaMA, or other architectures
-
Multi-Modal: Extend to include audio tone, facial expressions
-
Personalization: Learn individual hormone response patterns
-
Cross-Cultural: Adapt hormone profiles for different cultural contexts
If you use this work, please cite:
@misc{hormone_emotion_layer_2024,
title={Hormone-Based Emotion Layer for Transformer Language Models},
author={Your Name},
year={2024},
howpublished={\url{https://github.com/your-repo}}
}MIT License - See LICENSE for details.
- Hugging Face for the Transformers library
- The T5 team at Google Research
- Neuroscience research on the endocrine system's role in emotion
Built with ๐งฌ and โค๏ธ for Emotionally Intelligent AI