--- title: Object.prototype.__proto__ slug: Web/JavaScript/Reference/Global_Objects/Object/proto translation_of: Web/JavaScript/Reference/Global_Objects/Object/proto original_slug: Web/JavaScript/Referencje/Obiekty/Object/proto ---
Ostrzeżenie: Zmiana [[Prototype]] obiektu, ze względu na sposób w jaki współczesny JavaScript optymalizuje dostęp do właściwości, jest bardzo powolną operacją (W każdej przeglądarce!). Efekty modyfikacji łańcucha dziedziczenia są rozległe, nie chodzi tu tylko o wydłużenie czasu potrzebnego na wykonanie operacji obj.__proto__ = ..., skutki wpływają na każdy fragment kodu który odwołuje się do jakiejkolwiek właściwości obiektu, którego [[Prototype]] został zmieniony. Dlatego jeżeli zależy ci na wydajności powinieneś unikać tej operacji. Zamiast tego, stwórz nowy obiekt z porządanym [[Prototype]] za pomocą {{jsxref("Object.create()")}}.
Ostrzeżenie: Mimo że w dzisiejszych czasach Object.prototype.__proto__ jest wspierany w niemal każdej przeglądarce, jego istnienie oraz zachowanie zostały ujednolicone w specyfikacji ECMAScript 2015 jedynie jako legacy feature aby zapewnić kompatybilność z przeglądarkami. Dla lepszego wsparcia rekomenduje się używanie {{jsxref("Object.getPrototypeOf()")}}.
Właściwość __proto__ obiektu {{jsxref("Object.prototype")}} jest operatorem dostępu (metoda getter i setter) która operuje na wewnętrznym [[Prototype]] (na obiekcie lub na {{jsxref("Global_Objects/null", "null")}}) obiektu do którego się odnosi.
Użycie __proto__ jest kontrowersyjne i podchodzi się do niego z niechęcią. Oryginalnie nigdy nie pojawiło się w specyfikacji EcmaScript, ale nowoczesne przeglądarki postanowiły mimo wszystko to zaimplementować. Dopiero niedawno właściwość __proto__ znalazła swoje miejsce w specyfikacji ECMAScript 2015 aby zapewnić kompatybilność z tymi przeglądarkami. Jest ona jednak przestarzała ze względu na {{jsxref("Object.getPrototypeOf")}}/{{jsxref("Reflect.getPrototypeOf")}} oraz {{jsxref("Object.setPrototypeOf")}}/{{jsxref("Reflect.setPrototypeOf")}} (choć modyfikowanie [[Prototype]] wciąż jest operacją powolną, która powinna być unikana przez wzgląd na wydajność).
Właściwość __proto__ może być również używana w notacji literałowej aby ustawić [[Prototype]] tworzonego obiektu, jako alterantywa do {{jsxref("Object.create()")}}. Zobacz: inicjalizator obiektu / notacja literałowa.
var Kolo = function () {};
var ksztalt = {};
var kolo = new Kolo();
// Ustawianie prototypu obiektu
// ZDEPRECJONOWANE. Używamy tego tylko dla przykładu. NIE RÓB TEGO w prawdziwym kodzie.
ksztalt.__proto__ = kolo;
// Sprawdzenie prototypu obiektu
console.log(ksztalt.__proto__ === kolo); // true
var ksztalt = function () {};
var p =
{
a: function ()
{
console.log('aaa');
}
};
ksztalt.prototype.__proto__ = p;
var kolo = new ksztalt();
kolo.a(); // aaa
console.log(ksztalt.prototype === kolo.__proto__); // true
// albo
var ksztalt = function () {};
var p =
{
a: function ()
{
console.log('aaa');
}
};
var kolo = new ksztalt();
kolo.__proto__ = p;
circle.a(); // aaa
console.log(ksztalt.prototype === kolo.__proto__); // false
// albo
function ksztalt() {};
ksztalt.prototype.a = function ()
{
console.log('aaa');
}
var kolo = new ksztalt();
kolo.a(); // aaa
console.log(kolo.__proto__ === ksztalt.prototype); // true
// albo
var ksztalt = function () {};
ksztalt.prototype.a = function ()
{
console.log('aaa');
}
var kolo =
{
__proto__: ksztalt.prototype
};
kolo.a(); // aaa
console.log(kolo.__proto__ === ksztalt.prototype); // true
Uwaga: __proto__ zapisujemy jako dwie podłogi, następnie pięć liter "proto", następnie dwie kolejne podłogi.
Metoda getter właściwości __proto__ daje nam dostęp do wewnętrznej wartości [[Prototype]] obiektu. Dla obiektów stworzonych przy użyciu literału jest to {{jsxref("Object.prototype")}}. Dla tablic stworzonych przy użyciu literału jest to {{jsxref("Array.prototype")}}. Dla funkcji ta wartość to {{jsxref("Function.prototype")}}. Dla obiektów stworzonych przy użyciu new Funkcja, gdzie Funkcja to jeden z wbudowanych konstruktorów dostarczanych przez JavaScript ({{jsxref("Array")}}, {{jsxref("Boolean")}}, {{jsxref("Date")}}, {{jsxref("Number")}}, {{jsxref("Object")}}, {{jsxref("String")}}, i tak dalej — wliczając nowe konstrukotry, które mogą zostać dodane w przyszłości), ta wartość to zawsze Funkcja.prototype. Dla obiektów stworzonych przy użyciu new Funkcja, gdzie Funkcja to funkcja zdefiniowana w kodzie, wartość ta przyjmuje taką samą wartość jak Funkcja.prototype.
Metoda setter właściwości __proto__ umożliwia modyfikowanie [[Prototype]] obiektu. W tym celu obiekt musi być roszerzalny według funkcji {{jsxref("Object.isExtensible()")}}, jeżeli nie jest {{jsxref("Global_Objects/TypeError", "TypeError")}} zostanie wyrzucony. Dostarczana wartość musi być obiektem albo typem {{jsxref("Global_Objects/null", "null")}}. Podanie jakiejkolwiek innej wartości nie zrobi nic.
Aby zrozumieć w jaki sposób prototypy używane są do dziedziczenia, zobacz artykuł o dziedziczeniu oraz łańcuchu prototypów.
Właściwość __proto__ jest prostym operatorem pamięci na {{jsxref("Object.prototype")}} składającym się z metody getter i setter. Dostęp do właściwości __proto__ który ostatecznie konsultuje się z {{jsxref("Object.prototype")}} znajdzie tę właściwość, ale dostęp który nie konsultuje {{jsxref("Object.prototype")}} nie znajdzie jej. Jeżeli jakaś inna właściwość __proto__ zostanie znaleziona, zanim {{jsxref("Object.prototype")}} zostanie skonsultowany, to właściwość ta przesłoni tą znalezioną w {{jsxref("Object.prototype")}}.
| Specification | Status | Comment |
|---|---|---|
| {{SpecName('ES2015', '#sec-additional-properties-of-the-object.prototype-object', 'Object.prototype.__proto__')}} | {{Spec2('ES2015')}} | Dołączony (normatywnie) jako jeden z dodatkowych ECMAScript legacy features dla przeglądarek (zauważ że specyfikacja jedynie ujednoliciła coś, co było już zaimplementowane w przeglądarkach). |
| {{SpecName('ESDraft', '#sec-additional-properties-of-the-object.prototype-object', 'Object.prototype.__proto__')}} | {{Spec2('ESDraft')}} |
| Feature | Chrome | Firefox (Gecko) | Internet Explorer | Opera | Safari |
|---|---|---|---|---|---|
| Basic support | {{CompatVersionUnknown}} | {{CompatVersionUnknown}} | {{CompatIE("11")}} | {{CompatVersionUnknown}} | {{CompatVersionUnknown}} |
| Feature | Android | Chrome for Android | Firefox Mobile (Gecko) | IE Mobile | Opera Mobile | Safari Mobile |
|---|---|---|---|---|---|---|
| Basic support | {{CompatVersionUnknown}} | {{CompatVersionUnknown}} | {{CompatVersionUnknown}} | {{CompatVersionUnknown}} | {{CompatVersionUnknown}} | {{CompatVersionUnknown}} |
Mimo, że specyfikacja ECMAScript 2015 określa iż wsparcie dla __proto__ jest wymagane tylko dla przeglądarek internetowych (w zasadzie normatywnie), to inne środowiska równieź mogą wspierać tę funkcjonalność.