TypeError: "x" is not a function
JavaScript の例外 "is not a function" は、値を関数として呼び出そうとしたが、その値が実際には関数ではなかった場合に発生します。
エラーメッセージ
TypeError: "x" is not a function. (V8-based & Firefox & Safari)
エラーの種類
TypeError
エラーの原因
関数でないものを、関数呼び出ししようとした際に発生するエラーです。また適切な関数が定義されていることを期待されているが、定義されていない場合も発生します。
関数名にタイプミスがないでしょうか?あるいは、メソッドを呼び出そうとしているオブジェクトが、その関数を持っていないのではないでしょうか? 例えば、JavaScript の Object オブジェクトには map 関数はありませんが、Array オブジェクトにはあります。
多くの組み込み関数はコールバック関数を必要とします。これらのメソッドを正しく呼び出すためには、関数を引数に指定する必要があります。
-
ArrayもしくはTypedArrayオブジェクトを操作する場合:
例
>関数名のタイプミス
次のように関数名を間違えている場合に発生します。なおこのミスは非常に多く発生します。
const x = document.getElementByID("foo");
// TypeError: document.getElementByID is not a function
正しい関数名は getElementById です。
const x = document.getElementById("foo");
間違ったオブジェクトに対する関数呼び出し
いくつかのメソッドは、引数に関数が指定されていることを期待していて、しかも特定のオブジェクトの上でのみ正しく動作するものがあります。この典型例が Array.prototype.map() で、これは Array オブジェクトでのみ正しく動作します。
const obj = { a: 13, b: 37, c: 42 };
obj.map((num) => num * 2);
// TypeError: obj.map is not a function
オブジェクトではなく、配列を利用しましょう。
const numbers = [1, 4, 9];
numbers.map((num) => num * 2); // [2, 8, 18]
すでに存在するプロパティと名前を共有する関数
クラスを作るとき、プロパティと関数が同じ名前になることがあります。関数を呼び出すと、コンパイラーは関数が存在するのをやめたように考えます。
function Dog() {
this.age = 11;
this.color = "black";
this.name = "Ralph";
return this;
}
Dog.prototype.name = function (name) {
this.name = name;
return this;
};
const myNewDog = new Dog();
myNewDog.name("Cassidy"); // TypeError: myNewDog.name is not a function
代わりに異なるプロパティ名を使ってください。
function Dog() {
this.age = 11;
this.color = "black";
this.dogName = "Ralph"; // this.dogName を .name の代わりに使用
return this;
}
Dog.prototype.name = function (name) {
this.dogName = name;
return this;
};
const myNewDog = new Dog();
myNewDog.name("Cassidy"); // Dog { age: 11, color: 'black', dogName: 'Cassidy' }
乗算での括弧の使用
数学では、 2 × (3 + 5) を 2*(3 + 5) または単に 2(3 + 5) と書くことができます。
後者を使用するとエラーが発生します。
const sixteen = 2(3 + 5);
console.log(`2 x (3 + 5) is ${sixteen}`);
// Uncaught TypeError: 2 is not a function
このコードは * 演算子を追加すると修正できます。
const sixteen = 2 * (3 + 5);
console.log(`2 x (3 + 5) is ${sixteen}`);
// 2 x (3 + 5) is 16
正しくエクスポートされたモジュールをインポートする
正しくモジュールをインポートしていることを確認してください。
helpers ライブラリーの例 (helpers.js)
function helpers() {}
helpers.groupBy = function (objectArray, property) {
return objectArray.reduce((acc, obj) => {
const key = obj[property];
acc[key] ??= [];
acc[key].push(obj);
return acc;
}, {});
};
export default helpers;
正しい import の使い方 (App.js):
import helpers from "./helpers";