ではここからは、前回の 「関数はオブジェクト」練習問題(レベル1〜4) の
模範解答+ステップごとの解説 を順番に紹介します。
(全コードはブラウザの DevTools などでそのまま実行できます)
レベル1:関数は「変数に入る」値
✅ 問題1-1:関数を変数に代入して呼び出す
function hello() {
return "こんにちは!";
}
// ① hello関数を別の変数に代入
let greet = hello;
// ② greetを呼び出す
console.log(greet()); // → こんにちは!
JavaScript🧠 解説
helloという関数は、実際は「関数オブジェクト」を変数helloに代入した状態。let greet = hello;により、greetも同じ関数を参照。greet()を呼ぶと、元の関数とまったく同じ動作をする。
➡️ 関数はオブジェクト(値)だから、変数に入れて別名で使える。
✅ 問題1-2:無名関数を変数に代入して使う
let sum = function(a, b) {
return a + b;
};
console.log(sum(3, 5)); // → 8
JavaScript🧠 解説
function(a, b){ ... }には名前がない(=無名関数)。- これを変数
sumに入れているので、sumがその関数名の代わり。 - 呼び出すときは
sum()でOK。
➡️ 「関数=値」なので、名前を付けずにそのまま代入も可能。
✅ 問題1-3:関数を上書きしてみよう
function test() {
return "OK";
}
test = "上書きされました";
console.log(test); // → "上書きされました"
JavaScript🧠 解説
- JavaScriptでは、関数も「変数」扱いなので上書き可能。
- 実務では混乱のもとになるため、基本は上書きしない。
➡️ 「関数も変数」という点を実感できる例。
レベル2:関数を「渡す」ことができる
✅ 問題2-1:関数を引数として受け取る
function greet(name, formatter) {
console.log("Hello, " + formatter(name));
}
function upper(str) {
return str.toUpperCase();
}
greet("taro", upper); // → Hello, TARO
JavaScript🧠 解説
formatterは「引数として受け取った関数」。formatter(name)で呼び出すことで、処理内容を差し替えられる。
➡️ 関数を引数に渡すと、動作を柔軟に切り替えられる。
✅ 問題2-2:無名関数を直接渡す
function greet(name, formatter) {
console.log("Hello, " + formatter(name));
}
greet("太郎", function(n) {
return "山田" + n;
});
// → Hello, 山田太郎
JavaScript🧠 解説
- 無名関数をその場で渡すことで、一度きりの処理をすぐに書ける。
- 関数を「値」として直接渡している形。
➡️ “コールバック関数” の基礎。
✅ 問題2-3:関数を複数の場面で再利用
function double(n) {
return n * 2;
}
function processArray(arr, fn) {
let result = [];
for (let i = 0; i < arr.length; i++) {
result.push(fn(arr[i]));
}
return result;
}
console.log(processArray([1,2,3], double)); // → [2,4,6]
console.log(processArray([1,2,3], function(n){ return n + 10; })); // → [11,12,13]
JavaScript🧠 解説
fnは配列の要素ごとに適用される関数。- 渡す関数を変えるだけで結果が変わる!
➡️ 高い再利用性を持つ「高階関数」の考え方。
レベル3:関数を「返す」こともできる
✅ 問題3-1:関数を返す関数
function makeMultiplier(factor) {
return function(x) {
return x * factor;
};
}
const triple = makeMultiplier(3);
console.log(triple(5)); // → 15
JavaScript🧠 解説
makeMultiplierは「掛け算する関数」を作って返す。factorの値を覚えたまま動く(=クロージャ)。
➡️ 「関数を作る関数」=高階関数のパターン。
✅ 問題3-2:関数にプロパティを持たせる
function counter() {
return counter.count++;
}
counter.count = 1;
console.log(counter()); // 1
console.log(counter()); // 2
console.log(counter()); // 3
JavaScript🧠 解説
counterは関数だけど、counter.countというプロパティを持つ。- 関数もオブジェクトなので、プロパティを自由に付けられる。
➡️ 「関数もオブジェクト」という事実を実感。
✅ 問題3-3:関数を生成してフィルタ処理
function greaterThan(threshold) {
return function(x) {
return x > threshold;
};
}
const gt10 = greaterThan(10);
console.log([5, 12, 9, 15].filter(gt10)); // → [12,15]
JavaScript🧠 解説
greaterThan(10)は「10より大きいか判定する関数」を返す。.filter()に渡して使うと、条件を柔軟に切り替えられる。
➡️ 関数を動的に作る → 条件の使い回しが簡単。
レベル4:実務で役立つ応用パターン
✅ 問題4-1:フォーム検証関数を切り替える
function validate(value, rule) {
return rule(value);
}
function isNotEmpty(v) { return v.trim() !== ""; }
function isEmail(v) { return v.includes("@"); }
console.log(validate("test@example.com", isEmail)); // true
console.log(validate(" ", isNotEmpty)); // false
JavaScript🧠 解説
validateは「何をチェックするか」をrule関数に任せている。- 新しいルールを追加しても
validateは変えずに再利用できる。
➡️ 実務でよく使われる「ルール差し替え型」設計。
✅ 問題4-2:データ整形(APIレスポンスの加工)
function transformData(data, formatter) {
return data.map(formatter);
}
const users = [
{ name: "Taro", age: 25 },
{ name: "Hanako", age: 30 }
];
const formatted = transformData(users, function(u) {
return `${u.name}(${u.age}歳)`;
});
console.log(formatted); // → ["Taro(25歳)", "Hanako(30歳)"]
JavaScript🧠 解説
.map()の中で、渡した関数が1件ずつ実行される。formatterを変えるだけで出力形式を自在に変更。
➡️ UI整形やAPI加工など、現場で多用される。
✅ 問題4-3:関数の組み合わせ(関数合成)
function compose(f, g) {
return function(x) {
return f(g(x));
};
}
function double(x) { return x * 2; }
function square(x) { return x * x; }
const doubleThenSquare = compose(square, double);
console.log(doubleThenSquare(3)); // → 36
JavaScript🧠 解説
compose(f,g)は「f(g(x))を返す関数」を作る。- このように関数を組み合わせて処理を組み立てられる。
➡️ 関数型プログラミングの基本思想。
総まとめ
| レベル | 学べること | キーポイント |
|---|---|---|
| 1 | 関数は値 | 変数に代入できる |
| 2 | 関数を渡す | コールバック・柔軟な設計 |
| 3 | 関数を返す | クロージャ・高階関数 |
| 4 | 実務応用 | 検証・整形・関数合成 |
💡 理解を深めるコツ
- 1つの関数を「値」として扱う感覚をつかむこと。
- console.log で中身を確認しながら、「参照がどう動くか」を観察する。
- 次の段階では「アロー関数」「クロージャの詳細」「thisの扱い」などを学ぶとスムーズです。
