Files
2nd/10_Wiki/Topics/AI_and_ML/Recommendation-Systems.md
koriweb d8a80f6272 chore(wiki): dangling 링크 canonical 정규화 (768파일/1200건)
이름만 다른(표기 변형) [[위키링크]]를 대상 문서의 canonical 제목으로 치환해
끊겼던 1,200개 링크를 연결. 제목/파일명 정규화 일치만 적용하고 별칭 매칭은
과병합 위험으로 제외(애매성 가드). 원본은 _link_reconcile_backup/ 에 백업.
도구: Datacollect/scripts/link_reconcile_apply.mjs

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-08 12:24:15 +09:00

216 lines
8.1 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
---
id: wiki-2026-0508-recommendation-systems
title: Recommendation Systems
category: 10_Wiki/Topics
status: verified
canonical_id: self
aliases: [RecSys, Recommender Systems, Recommendation Engine]
duplicate_of: none
source_trust_level: A
confidence_score: 0.9
verification_status: applied
tags: [recsys, machine-learning, ranking, retrieval]
raw_sources: []
last_reinforced: 2026-05-10
github_commit: pending
tech_stack:
language: python
framework: pytorch
---
# Recommendation Systems
## 매 한 줄
> **"매 user × item 의 relevance prediction at scale"**. 매 collaborative filtering (Netflix Prize 2009) → matrix factorization → deep two-tower / sequential / generative recsys. 2026 현재 매 industrial stack 의 multi-stage (retrieval → ranking → re-ranking), 매 LLM-augmented (semantic ID, generative recsys, LLM reranker).
## 매 핵심
### 매 paradigms
- **Content-based**: item features × user profile (cold-start friendly).
- **Collaborative filtering (CF)**: user-item interactions only.
- **Memory-based**: user-user / item-item KNN.
- **Model-based**: matrix factorization (MF, ALS, SVD++).
- **Hybrid**: CF + content (LightFM, DCN).
- **Deep**:
- **Two-tower**: user-tower / item-tower → dot product (retrieval).
- **Sequential**: SASRec, BERT4Rec, GRU4Rec — 매 user history sequence modeling.
- **DIN/DIEN**: attention over user behaviors (Alibaba).
- **Graph**: PinSage, LightGCN.
- **Generative recsys (2024-2026)**: TIGER, semantic ID, LLM-as-recommender.
### 매 pipeline (industrial)
1. **Candidate generation (retrieval)**: 100M items → 1000 (two-tower ANN, FAISS / ScaNN).
2. **Ranking**: 1000 → 100 (heavy DCN / DIN, full features).
3. **Re-ranking**: 100 → 10 (diversity, business rules, MMR, RL).
4. **Serving**: <100ms p99.
### 매 metrics
- **Offline**: Recall@K, NDCG@K, MAP, AUC, MRR.
- **Online (A/B)**: CTR, conversion, dwell time, session length, retention.
- **Diversity / fairness**: ILD (intra-list diversity), exposure parity.
### 매 응용
1. E-commerce (Amazon, Coupang, Taobao).
2. Video / music (YouTube, TikTok, Spotify).
3. Social feed (Facebook, Twitter/X, LinkedIn).
4. News (Toutiao, Yahoo News).
5. Ads (Google Ads ranking).
## 💻 패턴
### Matrix factorization (implicit ALS)
```python
import implicit
from scipy.sparse import csr_matrix
# user-item interactions (rows=users, cols=items)
ui = csr_matrix(interactions) # 1.0 for click, weighted by dwell
model = implicit.als.AlternatingLeastSquares(
factors=128, regularization=0.01, iterations=20, use_gpu=True,
)
model.fit(ui)
recs = model.recommend(userid=42, user_items=ui[42], N=10)
```
### Two-tower retrieval (PyTorch)
```python
import torch
import torch.nn as nn
class TwoTower(nn.Module):
def __init__(self, n_users, n_items, dim=128):
super().__init__()
self.u_emb = nn.Embedding(n_users, dim)
self.i_emb = nn.Embedding(n_items, dim)
self.u_mlp = nn.Sequential(nn.Linear(dim, dim), nn.ReLU(), nn.Linear(dim, dim))
self.i_mlp = nn.Sequential(nn.Linear(dim, dim), nn.ReLU(), nn.Linear(dim, dim))
def user_repr(self, u): return nn.functional.normalize(self.u_mlp(self.u_emb(u)), dim=-1)
def item_repr(self, i): return nn.functional.normalize(self.i_mlp(self.i_emb(i)), dim=-1)
def forward(self, u, i_pos, i_negs):
u_v = self.user_repr(u).unsqueeze(1) # (B, 1, D)
pos = self.item_repr(i_pos).unsqueeze(1) # (B, 1, D)
negs = self.item_repr(i_negs) # (B, K, D)
logits = torch.cat([u_v @ pos.transpose(-1,-2), u_v @ negs.transpose(-1,-2)], dim=-1).squeeze(1)
labels = torch.zeros(u.size(0), dtype=torch.long, device=u.device)
return nn.functional.cross_entropy(logits / 0.07, labels) # in-batch + sampled negs
```
### ANN retrieval with FAISS
```python
import faiss, numpy as np
item_vecs = model.item_repr(torch.arange(n_items)).detach().cpu().numpy()
index = faiss.IndexFlatIP(128) # inner product
index.add(item_vecs)
def retrieve(user_vec, k=1000):
D, I = index.search(user_vec[None, :], k)
return I[0]
```
### SASRec (sequential recsys)
```python
class SASRec(nn.Module):
def __init__(self, n_items, dim=64, max_len=200, n_heads=2, n_layers=2):
super().__init__()
self.item_emb = nn.Embedding(n_items + 1, dim, padding_idx=0)
self.pos_emb = nn.Embedding(max_len, dim)
layer = nn.TransformerEncoderLayer(dim, n_heads, batch_first=True, activation="gelu")
self.tr = nn.TransformerEncoder(layer, n_layers)
def forward(self, seq): # (B, L)
L = seq.size(1)
pos = torch.arange(L, device=seq.device).unsqueeze(0)
x = self.item_emb(seq) + self.pos_emb(pos)
mask = torch.triu(torch.ones(L, L), diagonal=1).bool().to(seq.device)
h = self.tr(x, mask=mask)
# next-item prediction
return h @ self.item_emb.weight.T # (B, L, V)
```
### DIN-style attention over user history
```python
class DINAttention(nn.Module):
def __init__(self, dim):
super().__init__()
self.mlp = nn.Sequential(nn.Linear(4*dim, dim), nn.ReLU(), nn.Linear(dim, 1))
def forward(self, target, history, mask):
# target (B, D), history (B, L, D), mask (B, L)
T = target.unsqueeze(1).expand_as(history)
feats = torch.cat([T, history, T - history, T * history], dim=-1)
attn = self.mlp(feats).squeeze(-1)
attn = attn.masked_fill(~mask, -1e9).softmax(-1)
return (attn.unsqueeze(-1) * history).sum(1)
```
### LLM reranker (2026)
```python
from anthropic import Anthropic
client = Anthropic()
def llm_rerank(user_history, candidates):
msg = client.messages.create(
model="claude-opus-4-7",
max_tokens=500,
messages=[{"role": "user", "content": f"""
User watched: {user_history}
Rerank these candidates by relevance, return top-10 IDs only as JSON array:
{candidates}
"""}],
)
return parse_json(msg.content[0].text)
```
### Implicit feedback BPR loss
```python
def bpr_loss(u, i_pos, i_neg, model):
s_pos = (model.u(u) * model.i(i_pos)).sum(-1)
s_neg = (model.u(u) * model.i(i_neg)).sum(-1)
return -torch.log(torch.sigmoid(s_pos - s_neg) + 1e-12).mean()
```
## 매 결정 기준
| 상황 | Approach |
|---|---|
| Cold-start (new user / item) | content-based + popularity |
| Small data (<10k users) | item-item KNN |
| Mid (10k-1M) | ALS / LightFM |
| Large (>1M, sequence behavior) | two-tower retrieval + DIN/SASRec ranking |
| Strict latency budget | two-tower + ANN |
| Need explanation / control | LLM reranker on top-100 |
| Cross-domain (text + image) | multimodal embeddings (CLIP-style) |
**기본값**: 매 industrial 의 two-tower retrieval + DCN/DIN ranking + business-rule rerank, 매 ANN (FAISS / ScaNN), 매 implicit feedback + sampled softmax. 매 LLM-as-reranker 의 emerging 2026 pattern for top-K refinement.
## 🔗 Graph
- 부모: [[Machine-Learning]] · [[Information Retrieval]]
- 변형: [[Collaborative-Filtering]]
- 응용: [[E-commerce]]
- Adjacent: [[Embeddings]] · [[FAISS]]
## 🤖 LLM 활용
**언제**: cold-start (zero-shot recommendation from item description), reranker on top-100, explanation generation, semantic ID encoding.
**언제 X**: full-funnel retrieval at scale (latency / cost prohibitive). 매 LLM 의 reranker only, 매 retrieval 의 ANN.
## ❌ 안티패턴
- **Random negative sampling only**: easy negatives, model 의 saturate — use hard negatives + in-batch negatives.
- **Train on biased logged data**: position bias / popularity bias not corrected → IPS / counterfactual.
- **Offline metric chasing**: NDCG up but online CTR flat — online A/B 의 truth.
- **Cold-start ignore**: pure CF 의 fail on new items — hybrid fallback.
- **No exploration**: greedy ranking → filter bubble. ε-greedy / Thompson / contextual bandit.
- **Single objective**: CTR-only optimization 의 clickbait. Multi-objective (dwell, retention).
## 🧪 검증 / 중복
- Verified (Koren 2009 Netflix Prize, He LightGCN 2020, Kang SASRec 2018, Zhou DIN 2018, Covington YouTube DNN 2016, Google TIGER 2024).
- 신뢰도 A.
## 🕓 Changelog
| 날짜 | 변경 |
|---|---|
| 2026-05-08 | Phase 1 |
| 2026-05-10 | Manual cleanup — full canonical recsys with two-tower/SASRec/DIN/LLM-reranker |