String
たとえば、インスタンスにメソッドを追加することは可能ですか?
x = "123"
x.method = function() { console.log("test") }
x.method()
String
たとえば、インスタンスにメソッドを追加することは可能ですか?
x = "123"
x.method = function() { console.log("test") }
x.method()
はい、できます。ただし、最初に文字列プリミティブを取得して文字列インスタンスにする必要があります。
x = new String("123");
x.method = function() { console.log("test") };
x.method();
JavaScript には、文字列プリミティブと文字列インスタンスの両方があります。元のコードでは、次のように記述しました。
x.method = ...;
...文字列プリミティブは変数から取得x
され、メソッドを追加した文字列インスタンスに昇格されましたが、文字列インスタンスは変数に格納されてx
いないため、呼び出そうとしたときにメソッドがありませんでした. (はい、これは直感に反します。)
上記で使用new String(...)
することにより、実際に文字列インスタンスを取得して に格納しx
ます。次に、これは適切なオブジェクトなので、プロパティを追加できます。
String.prototype
次のように、にメソッドを追加することもできます。
String.prototype.capitalize = function() {
return this.substring(0, 1).toUpperCase() + this.substring(1);
};
console.log("testing".capitalize()); // "Testing"
これは悪い習慣だと感じる人もいます。他の人は、まさにそれがプロトタイプの継承を持っている理由であり、プロトタイプを使用して物事を拡張できると言います。私は人々が を強化することによる問題を見たことがありませんが、人々が をString.prototype
強化するときに問題があるようです(人々は を誤用Array.prototype
することを主張するため) .for-in
Object.prototype
文字列と数値は自動ボックス化されたプリミティブです。つまり、オブジェクト指向操作を実行すると、「文字列」および「数値」クラスとしてキャストされますが、すぐにボックス化されません。
コードは次のように評価されます。
x = "123"
(new String(x)).method = function() { console.log("test") }
(new String(x)).method() // Error
まったく異なる String オブジェクトを扱っているため、2 番目の呼び出しは失敗しています。TJ が述べたように、String オブジェクトを作成することでこれを回避できますがx
、これは一般的または推奨される方法ではありません。
メソッドを に追加することで、すべての文字列を拡張できますString.prototype
。
x = "123"
String.prototype.method = function() { console.log("test") }
x.method()
この呼び出しは と同じように評価されます(new String(x)).method()
が、そのメソッドはプロトタイプに存在するため、呼び出されます。
ECMA5 を使用して新しいプロパティを定義できます
Object.defineProperty(String.prototype, "test", {
value: function test() { console.log('test:',this) },
configurable: true,
enumerable: false,
writeable: true
});
完全な回答を参照してください: プロトタイプを変更せずにコア タイプを拡張する