$derived - シンプルな計算
主に、一行で表現できる計算に使用します。
<script>
let count = $state(0);
let doubled = $derived(count * 2);
let isEven = $derived(count % 2 === 0);
</script>
<p>カウント: {count}</p>
<p>2倍: {doubled}</p>
<p>偶数: {isEven ? 'はい' : 'いいえ'}</p>
いつ使う?
- 数式計算:
price * 1.1
- 比較演算:
score > 80
- 文字列結合:
firstName + ' ' + lastName
- 単純な条件:
age >= 18 ? '成人' : '未成年'
$derived.by - 複雑な計算
$derivedとの使い分けとして、複数行や複雑なロジックには $derived.by
を使用します。
<script>
let tasks = $state([
{ name: 'タスク1', done: false },
{ name: 'タスク2', done: true }
]);
let progress = $derived.by(() => {
const total = tasks.length;
const completed = tasks.filter(t => t.done).length;
const percentage = total > 0 ? (completed / total) * 100 : 0;
return {
total,
completed,
percentage: Math.round(percentage)
};
});
</script>
<p>進捗: {progress.completed}/{progress.total} ({progress.percentage}%)</p>
いつ使う?
- 配列の集計処理
- 複数の条件分岐
- オブジェクトの変換
- 複数ステップの計算
実用例での比較
ショッピングカート
<script>
let items = $state([
{ name: '商品A', price: 100, qty: 2 },
{ name: '商品B', price: 200, qty: 1 }
]);
// $derived - シンプルな計算
let itemCount = $derived(items.length);
// $derived.by - 複雑な計算
let summary = $derived.by(() => {
let subtotal = 0;
let totalQty = 0;
for (const item of items) {
subtotal += item.price * item.qty;
totalQty += item.qty;
}
const tax = subtotal * 0.1;
const total = subtotal + tax;
return {
subtotal,
tax: Math.round(tax),
total: Math.round(total),
totalQty
};
});
</script>
ユーザー表示名
<script>
let user = $state({ firstName: '太郎', lastName: '山田', isVip: true });
let settings = $state({ showFullName: true, showVipBadge: true });
// $derived.by - 条件分岐が複雑
let displayName = $derived.by(() => {
let name = settings.showFullName
? `${user.lastName} ${user.firstName}`
: user.firstName;
if (settings.showVipBadge && user.isVip) {
name += ' ⭐VIP';
}
return name;
});
</script>
更新タイミング
- state変更時:関連するderived全てに変更通知
- 表示時:実際に値を計算
<script>
let count = $state(0);
// countが0→1の時のみ更新(false→true)
// 1→2の時は更新されない(true→true)
let hasItems = $derived(count > 0);
</script>
<!-- hasItemsが変わった時だけテキスト更新 -->
<button>アイテム数: {hasItems ? 'あり' : 'なし'}</button>
derived値の一時的な変更
derived値は一時的に上書きできます(いいね機能など)
<script>
let post = $state({ likes: 10 });
let likes = $derived(post.likes);
async function addLike() {
likes += 1; // 画面を即座に更新
try {
await api.like(post.id);
post.likes = likes; // サーバー処理成功
} catch {
likes -= 1; // 失敗時に元に戻す
}
}
</script>
使い分け表
状況 | 使用 |
---|---|
単純計算 | $derived |
文字列結合 | $derived |
配列処理 | $derived.by |
条件分岐多数 | $derived.by |
複数ステップ | $derived.by |