Długość obiektu JavaScript


2383

Mam obiekt JavaScript, czy istnieje wbudowany lub zaakceptowany najlepszy sposób uzyskania długości tego obiektu?

const myObject = new Object();
myObject["firstname"] = "Gareth";
myObject["lastname"] = "Simpson";
myObject["age"] = 21;

15
Literały obiektów w javascript są domyślnie tablicami asocjacyjnymi, np. Object.propertyName.propertyValue jest taki sam jak object [propertyName] [propertyValue]
neitony

6
Dodano jedną linijkę w Underscore.js, która robi to: stackoverflow.com/a/11346637/11236
ripper234

31
Gdy odpowiedzią na wiersz jest użycie Object.keys (myArray) .length, jak powiedział @aeosynth.
Ranadheer Reddy

67
ok, a co powieszObject.keys(obj).length
Muhammad Umer

5
Dlaczego wartość object.length jest nieprawidłowa? Zwraca prawidłowy wynik dla mnie.
Adrian M

Odpowiedzi:


2622

Najbardziej niezawodną odpowiedzią (tj. Która uchwyci zamiar tego, co próbujesz zrobić, powodując jak najmniej błędów), byłoby:

Object.size = function(obj) {
    var size = 0, key;
    for (key in obj) {
        if (obj.hasOwnProperty(key)) size++;
    }
    return size;
};

// Get the size of an object
var size = Object.size(myObj);

JavaScript zawiera pewną konwencję, według której nie dodajesz elementów do Object.prototype , ponieważ może on przerywać wyliczenia w różnych bibliotekach. Jednak dodawanie metod do Object jest zwykle bezpieczne.


Oto aktualizacja z 2016 r. I powszechne wdrożenie ES5 i późniejszych wersji. W przypadku IE9 + i wszystkich innych współczesnych przeglądarek obsługujących ES5 + możesz użyć Object.keys()powyższego kodu:

var size = Object.keys(myObj).length;

Nie musi to modyfikować żadnego istniejącego prototypu, ponieważ Object.keys()jest teraz wbudowany.

Edycja : Obiekty mogą mieć właściwości symboliczne, których nie można zwrócić za pomocą metody Object.key. Zatem odpowiedź byłaby niepełna bez wspominania o nich.

Typ języka został dodany do języka, aby utworzyć unikalne identyfikatory właściwości obiektu. Główną zaletą typu Symbol jest zapobieganie nadpisywaniu.

Object.keyslub Object.getOwnPropertyNamesnie działa dla właściwości symbolicznych. Aby je zwrócić, musisz użyć Object.getOwnPropertySymbols.

var person = {
  [Symbol('name')]: 'John Doe',
  [Symbol('age')]: 33,
  "occupation": "Programmer"
};

const propOwn = Object.getOwnPropertyNames(person);
console.log(propOwn.length); // 1

let propSymb = Object.getOwnPropertySymbols(person);
console.log(propSymb.length); // 2

65
@Tres - Twój kod może zostać uszkodzony, jeśli ktoś przyjdzie i obejdzie właściwość „size”, nie wiedząc, że zadeklarowałeś go już gdzieś w kodzie, więc zawsze warto sprawdzić, czy jest już zdefiniowany
vsync

19
@vsync Masz rację. Zawsze należy wprowadzać niezbędne kontrole poczytalności :)
Tres

132
Dlaczego wszyscy to ignorują:Object.keys(obj).length
Muhammad Umer,

33
@MuhammadUmer Prawdopodobnie dlatego, że ta metoda nawet nie istniała, kiedy napisano tę odpowiedź. Nawet dzisiaj korzystanie z niego prawdopodobnie będzie wymagało wypełniania wieloskładnikowego w starych przeglądarkach.
Chris Hayes

21
@stonyau IE8, IE9, IE10 to martwe przeglądarki, które nie otrzymują wsparcia od Microsoft. Użytkownik IE8, IE9, IE10 otrzymuje powiadomienie od Microsoft, że korzysta ze starej, nieobsługiwanej przeglądarki i powinien oczekiwać, że coś nie będzie dla nich działać. support.microsoft.com/en-us/kb/3123303
Lukas Liesis

1705

Jeśli wiesz, że nie musisz się martwić hasOwnPropertyczekami, możesz to zrobić bardzo prosto:

Object.keys(myArray).length

23
Dlaczego nie? z tego co wiem, jest to standard: developer.mozilla.org/en/JavaScript/Reference/Global_Objects/…
vsync

104
To nie jest powszechnie stosowana metoda, ale możesz sprawdzić, która przeglądarka obsługuje tę tabelę .
aeosynth

51
Brak obsługi IE8 = nie start.
ripper234

22
czas na przejście na firefox = niestety zmiana nie oznacza, że ​​użytkownicy twojej witryny będą ...
mdup

82
@ ripper234 brak obsługi IE = czas na napełnianie
John Dvorak,

287

Zaktualizowano : Jeśli używasz Underscore.js (zalecane, jest lekki!), Możesz to zrobić

_.size({one : 1, two : 2, three : 3});
=> 3

Jeśli nie , i nie chcesz mieszać się z właściwościami obiektu z jakiegokolwiek powodu, a już używasz jQuery, wtyczka jest równie dostępna:

$.assocArraySize = function(obj) {
    // http://stackoverflow.com/a/6700/11236
    var size = 0, key;
    for (key in obj) {
        if (obj.hasOwnProperty(key)) size++;
    }
    return size;
};

7
_.size()było idealnym rozwiązaniem dla mojego projektu Meteor , który ma obsługę underscore.js.
tokyovariable

4
Używam podkreślenia, a ten post przypomniał mi, że nie używam go wystarczająco w tym projekcie. Jeśli zajmujesz się obiektami, powinieneś mieć plik underscore.js.
jbolanos

3
Podkreślenie> (wszystkie - ['lo-dash'])
Rayjax

underscorejs, rzeczy, które powinny być pod js :)
minhajul

1
@Babydead, aby odróżnić właściwości rzeczywiste obiektu od odziedziczonych. developer.mozilla.org/en/docs/Web/JavaScript/Reference/…
ripper234

56

Oto najbardziej rozwiązanie dla różnych przeglądarek.

Jest to lepsze niż zaakceptowana odpowiedź, ponieważ używa natywnych kluczy Object.keys, jeśli istnieje. Dlatego jest najszybszy dla wszystkich współczesnych przeglądarek.

if (!Object.keys) {
    Object.keys = function (obj) {
        var arr = [],
            key;
        for (key in obj) {
            if (obj.hasOwnProperty(key)) {
                arr.push(key);
            }
        }
        return arr;
    };
}

Object.keys(obj).length;

6
Object.keys()zwraca tablicę zawierającą nazwy tylko tych właściwości, które są policzalne. Jeśli chcesz tablicy z WSZYSTKIMI właściwościami, powinieneś użyć Object.getOwnPropertyNames()zamiast niej. Zobacz developer.mozilla.org/en/docs/Web/JavaScript/Reference/…
John Slegers,

35

Nie jestem ekspertem w dziedzinie JavaScript, ale wygląda na to, że będziesz musiał przeglądać elementy i liczyć je, ponieważ Object nie ma metody długości:

var element_count = 0;
for (e in myArray) {  if (myArray.hasOwnProperty(e)) element_count++; }

@palmsey: W uczciwości w stosunku do OP dokumentacja JavaScript w rzeczywistości wyraźnie odnosi się do używania zmiennych typu Object w ten sposób jako „tablice asocjacyjne”.


8
Nie będzie działać, ponieważ policzy również metody, które są dodawane przez prototyp.
Lajos Meszaros

30

Ta metoda pobiera wszystkie nazwy właściwości obiektu do tablicy, dzięki czemu można uzyskać długość tej tablicy, która jest równa długości kluczy obiektu.

Object.getOwnPropertyNames({"hi":"Hi","msg":"Message"}).length; // => 2

Metoda @PatrickRoberts keys nie zwraca właściwości z łańcucha prototypów. Więc dlaczego potrzeba hasOwnProperty tutaj. Również getOwnProperty zwróci ukryte właściwości, ponieważ długość jest w tablicy itp.
Muhammad Umer

24

Aby nie zadzierać z prototypem lub innym kodem, możesz zbudować i rozszerzyć własny obiekt:

function Hash(){
    var length=0;
    this.add = function(key, val){
         if(this[key] == undefined)
         {
           length++;
         }
         this[key]=val;
    }; 
    this.length = function(){
        return length;
    };
}

myArray = new Hash();
myArray.add("lastname", "Simpson");
myArray.add("age", 21);
alert(myArray.length()); // will alert 2

Jeśli zawsze korzystasz z metody add, właściwość length będzie poprawna. Jeśli obawiasz się, że Ty lub inni zapomnieliście o jego użyciu, możecie dodać licznik właściwości, który inni też opublikowali w metodzie długości.

Oczywiście zawsze możesz zastąpić metody. Ale nawet jeśli to zrobisz, Twój kod prawdopodobnie zawiedzie zauważalnie, co ułatwi debugowanie. ;)


Myślę, że jest to najlepsze rozwiązanie, ponieważ nie wymaga zapętlania z „for”, co może być kosztowne, jeśli tablica jest duża
Emeka Mbah

20

Oto jak i nie zapomnij sprawdzić, czy właściwość nie znajduje się w łańcuchu prototypów:

var element_count = 0;
for(var e in myArray)
    if(myArray.hasOwnProperty(e))
        element_count++;

20

Po prostu użyj tego, aby uzyskać length:

Object.keys(myObject).length

7
wyjaśnij, czym różni się twoja odpowiedź stackoverflow.com/a/6700/8632727
Patata,

3
Nie powinieneś też nazywać swojego obiektu myArray
Barry Michael Doyle

2
@BarryMichaelDoyle zmieniłem to :)
saurabhgoyal795

Dobrze, zawsze lepiej nazwać swoje zmienne zgodnie z tym, czym one są. Sprawia, że ​​Twój kod jest bardziej czytelny dla innych programistów.
Barry Michael Doyle,

4
Przed edycją „myArray” -> „myObject” było to identyczne z drugą najwyższą oceną odpowiedzi.
Yunnosch,

16

Oto zupełnie inne rozwiązanie, które będzie działać tylko w bardziej nowoczesnych przeglądarkach (IE9 +, Chrome, Firefox 4+, Opera 11.60+, Safari 5.1+)

Zobacz jsFiddle

Skonfiguruj klasę tablicy asocjacyjnej

/**
 * @constructor
 */
AssociativeArray = function () {};

// Make the length property work
Object.defineProperty(AssociativeArray.prototype, "length", {
    get: function () {
        var count = 0;
        for (var key in this) {
            if (this.hasOwnProperty(key))
                count++;
        }
        return count;
    }
});

Teraz możesz użyć tego kodu w następujący sposób ...

var a1 = new AssociativeArray();
a1["prop1"] = "test";
a1["prop2"] = 1234;
a1["prop3"] = "something else";
alert("Length of array is " + a1.length);

Myślę, że to nie jest bezpieczne. Na przykład nie może mieć elementu z kluczem „length”, instrukcja a1 [„length”] = „Hello world”; nie zapisuje wpisu. Również instrukcja a1 ["hasOwnProperty"] = "some prop"; totalnie zrywa funkcję
Panos Theof

3
@PanosTheof Nie sądzę, byś chciał, aby przechowywał wartość, jeśli używałeś lengthwłaściwości, każdy kod, który używałby jej, musiałby mieć pewność, że nie spróbuje zapisać wartości length, ale myślę, że byłby taki sam, gdyby był również standardowa tablica. Przesłonięcie hasOwnPropertydowolnego obiektu najprawdopodobniej spowodowałoby niepożądany wynik.
Ally

16

<script>
myObj = {"key1" : "Hello", "key2" : "Goodbye"};
var size = Object.keys(myObj).length;
console.log(size);
</script>

<p id="myObj">The number of <b>keys</b> in <b>myObj</b> are: <script>document.write(size)</script></p>

To działa dla mnie:

var size = Object.keys(myObj).length;

15

W niektórych przypadkach lepiej jest po prostu przechowywać rozmiar w osobnej zmiennej. Zwłaszcza jeśli dodajesz do tablicy jeden element w jednym miejscu i możesz łatwo zwiększyć rozmiar. Oczywiście działałoby to znacznie szybciej, jeśli trzeba często sprawdzać rozmiar.


15

Posługiwać się:

var myArray = new Object();
myArray["firstname"] = "Gareth";
myArray["lastname"] = "Simpson";
myArray["age"] = 21;
obj = Object.keys(myArray).length;
console.log(obj)


14

@palmsey: W uczciwości w stosunku do OP, dokumenty javascript w rzeczywistości jawnie odnoszą się do używania zmiennych typu Object w ten sposób jako „tablice asocjacyjne”.

I uczciwie dla @palmsey miał rację, nie są to tablice asocjacyjne, to zdecydowanie obiekty :) - wykonujące zadanie tablicy asocjacyjnej. Ale jeśli chodzi o szerszą kwestię, zdecydowanie masz do tego prawo zgodnie z tym dość pięknym artykułem, który znalazłem:

JavaScript „Tablice asocjacyjne” uważane za szkodliwe

Ale zgodnie z tym wszystkim, czy sama przyjęta odpowiedź nie jest złą praktyką?

Określ prototypową funkcję size () dla Object

Jeśli cokolwiek innego zostało dodane do Object .prototype, sugerowany kod zawiedzie:

<script type="text/javascript">
Object.prototype.size = function () {
  var len = this.length ? --this.length : -1;
    for (var k in this)
      len++;
  return len;
}
Object.prototype.size2 = function () {
  var len = this.length ? --this.length : -1;
    for (var k in this)
      len++;
  return len;
}
var myArray = new Object();
myArray["firstname"] = "Gareth";
myArray["lastname"] = "Simpson";
myArray["age"] = 21;
alert("age is " + myArray["age"]);
alert("length is " + myArray.size());
</script>

Nie sądzę, że ta odpowiedź powinna być zaakceptowana, ponieważ nie można ufać jej działaniu, jeśli masz inny kod działający w tym samym kontekście wykonania. Aby to zrobić solidnie, na pewno musisz zdefiniować metodę rozmiaru w myArray i sprawdzać typ elementów podczas iteracji przez nie.


13

Jeśli potrzebujesz asocjacyjnej struktury danych, która ujawnia swój rozmiar, lepiej użyj mapy zamiast obiektu.

const myMap = new Map();
myMap.set("firstname", "Gareth");
myMap.set("lastname", "Simpson");
myMap.set("age", 21);
myMap.size; // 3

11

Co powiesz na coś takiego -

function keyValuePairs() {
    this.length = 0;
    function add(key, value) { this[key] = value; this.length++; }
    function remove(key) { if (this.hasOwnProperty(key)) { delete this[key]; this.length--; }}
}

11

Jeśli mamy skrót

hash = {"a": "b", "c": "d"};

długość możemy uzyskać za pomocą długości kluczy, która jest długością skrótu:

klucze (skrót). długość


2
To świetna odpowiedź, jednak nie mogę znaleźć żadnej dokumentacji dla tej funkcji klawiszy. Nie mogę więc być pewny obsługi wielu przeglądarek.
chim

1
Niestety nie jest to tak dobra odpowiedź, jak na początku myślałem! Okazuje się, że funkcja klawiszy jest dostępna tylko w konsolach Chrome i Firefox. Jeśli wstawisz ten kod do skryptu, zakończy się niepowodzeniem z błędem Uncaught ReferenceError: klucze nie są zdefiniowane
chim


1
Czym różni się to od odpowiedzi aeosynth ?
Peter Mortensen

11
var myObject = new Object();
myObject["firstname"] = "Gareth";
myObject["lastname"] = "Simpson";
myObject["age"] = 21;
  1. Object.values ​​(myObject) .length
  2. Object.entries (myObject) .length
  3. Object.keys (myObject) .length

Który z nich jest szybszy spośród powyższych 3.
siluveru kiran kumar

Object.values ​​(myObject) .length
tdjprog

jak możemy powiedzieć, że Object.values ​​(myObject) .length jest szybszy czy jest jakiś przykład Dzięki, @tdjprog
siluveru kiran kumar

po prostu spróbuj tego w konsoli:var myObject = {}; for (let i=0; i<10000000; i++) myObject[i] = i;
tdjprog

dlaczego Object.values ​​(myObject) .length szybciej, gdzie jako Object.entries (myObject) .length nie daje danych wyjściowych nawet po jakimś czasie, jaki jest tego powód? Dzięki @tdjprog
siluveru kiran kumar

10

Jeśli używasz AngularJS 1.x, możesz robić to po AngularJS, tworząc filtr i używając kodu z dowolnego z innych przykładów, takich jak:

// Count the elements in an object
app.filter('lengthOfObject', function() {
  return function( obj ) {
    var size = 0, key;
    for (key in obj) {
      if (obj.hasOwnProperty(key)) size++;
    }
   return size;
 }
})

Stosowanie

W twoim kontrolerze:

$scope.filterResult = $filter('lengthOfObject')($scope.object)

Lub twoim zdaniem:

<any ng-expression="object | lengthOfObject"></any>

4
OP nie poprosił o wersję AngularJS. To nie jest prawidłowa odpowiedź na pytanie.
Francisco Hodge,


8

Jeśli nie chcesz obsługiwać przeglądarki Internet Explorer 8 lub starszej, możesz łatwo uzyskać liczbę właściwości obiektu, wykonując następujące dwa kroki:

  1. Uruchom albo, Object.keys()aby uzyskać tablicę zawierającą nazwy tylko tych właściwości, które są policzalne, lub Object.getOwnPropertyNames()jeśli chcesz także dołączyć nazwy właściwości, które nie są policzalne.
  2. Uzyskaj .lengthwłaściwość tej tablicy.

Jeśli musisz to zrobić więcej niż raz, możesz zawrzeć tę logikę w funkcji:

function size(obj, enumerablesOnly) {
    return enumerablesOnly === false ?
        Object.getOwnPropertyNames(obj).length :
        Object.keys(obj).length;
}

Jak korzystać z tej konkretnej funkcji:

var myObj = Object.create({}, {
    getFoo: {},
    setFoo: {}
});
myObj.Foo = 12;

var myArr = [1,2,5,4,8,15];

console.log(size(myObj));        // Output : 1
console.log(size(myObj, true));  // Output : 1
console.log(size(myObj, false)); // Output : 3
console.log(size(myArr));        // Output : 6
console.log(size(myArr, true));  // Output : 6
console.log(size(myArr, false)); // Output : 7

Zobacz także Fiddle, aby zobaczyć demo.


8

Użyj, Object.keys(myObject).lengthaby uzyskać długość obiektu / tablicy

var myObject = new Object();
myObject["firstname"] = "Gareth";
myObject["lastname"] = "Simpson";
myObject["age"] = 21;

console.log(Object.keys(myObject).length); //3

8
const myObject = new Object();
myObject["firstname"] = "Gareth";
myObject["lastname"] = "Simpson";
myObject["age"] = 21;

console.log(Object.keys(myObject).length)

// o/p 3

7

Odmianą niektórych z powyższych jest:

var objLength = function(obj){    
    var key,len=0;
    for(key in obj){
        len += Number( obj.hasOwnProperty(key) );
    }
    return len;
};

Jest to nieco bardziej elegancki sposób integracji hasOwnProp.


6

Oto inna wersja odpowiedzi Jamesa Cogana. Zamiast przekazywać argument, po prostu prototypuj klasę Object i popraw kod.

Object.prototype.size = function () {
    var size = 0,
        key;
    for (key in this) {
        if (this.hasOwnProperty(key)) size++;
    }
    return size;
};

var x = {
    one: 1,
    two: 2,
    three: 3
};

x.size() === 3;

Przykład jsfiddle: http://jsfiddle.net/qar4j/1/


6
Object.prototype- kiepski pomysł.
Dziad Borowy

@tborychowski czy możesz wyjaśnić dlaczego?
Mohamad

oto jeden artykuł: bit.ly/1droWrG . Nie twierdzę, że nie można tego zrobić, tylko że musisz znać wszystkie konsekwencje, zanim to zrobisz.
Dziad Borowy

Jeśli zamierzasz rozszerzyć wbudowane prototypy lub uzupełnić właściwość (np. Łatka małpy), zrób to poprawnie: w celu uzyskania zgodności z poprzednimi wersjami sprawdź, czy właściwość istnieje jako pierwsza, a następnie ustaw właściwość niepoliczalną, aby własne klucze zbudowanych obiektów nie są zanieczyszczone. Do metod używaj rzeczywistych metod . Moja rekomendacja: postępuj zgodnie z tymi przykładami, które pokazują, jak dodać metodę, która zachowuje się tak blisko, jak to możliwe, jak metody wbudowane.
user4642212

5

Możesz po prostu użyć Object.keys(obj).lengthdowolnego obiektu, aby uzyskać jego długość. Object.keys zwraca tablicę zawierającą wszystkie klucze obiektów (właściwości), które mogą się przydać do znalezienia długości tego obiektu na podstawie długości odpowiedniej tablicy. Możesz nawet napisać dla tego funkcję . Stańmy się kreatywni i napiszmy również metodę (wraz z bardziej wygodną właściwością gettera):

function objLength(obj)
{
  return Object.keys(obj).length;
}

console.log(objLength({a:1, b:"summit", c:"nonsense"}));

// Works perfectly fine
var obj = new Object();
obj['fish'] = 30;
obj['nullified content'] = null;
console.log(objLength(obj));

// It also works your way, which is creating it using the Object constructor
Object.prototype.getLength = function() {
   return Object.keys(this).length;
}
console.log(obj.getLength());

// You can also write it as a method, which is more efficient as done so above

Object.defineProperty(Object.prototype, "length", {get:function(){
    return Object.keys(this).length;
}});
console.log(obj.length);

// probably the most effictive approach is done so and demonstrated above which sets a getter property called "length" for objects which returns the equivalent value of getLength(this) or this.getLength()


3
Czym różni się to od odpowiedzi aeosynth ?
Peter Mortensen

To dlatego, że pokazuje, jak zrobić to jako funkcję i globalną metodę obiektową (bardziej zorientowaną obiektowo i używa jakiejś formy enkapsulacji); jednak odpowiedź aeosynth nie.
Mistyczne

Jeśli zamierzasz rozszerzyć wbudowane prototypy lub uzupełnić właściwość (np. Łatka małpy), zrób to poprawnie: w celu uzyskania zgodności z poprzednimi wersjami sprawdź, czy właściwość istnieje jako pierwsza, a następnie ustaw właściwość niepoliczalną, aby własne klucze zbudowanych obiektów nie są zanieczyszczone. Do metod używaj rzeczywistych metod . Moja rekomendacja: postępuj zgodnie z tymi przykładami, które pokazują, jak dodać metodę, która zachowuje się tak blisko, jak to możliwe, jak metody wbudowane.
user4642212

W jaki sposób pisanie metody jest „bardziej wydajne”?
user4642212

5

Zawsze możesz zrobić, Object.getOwnPropertyNames(myObject).lengthaby uzyskać taki sam wynik, jak w [].lengthprzypadku normalnej tablicy.


1
Object.keys()zwraca tablicę zawierającą nazwy tylko tych właściwości, które są policzalne. Jeśli chcesz tablicy z WSZYSTKIMI właściwościami, powinieneś użyć Object.getOwnPropertyNames()zamiast niej. Zobacz developer.mozilla.org/en/docs/Web/JavaScript/Reference/…
John Slegers

3
Czym różni się to od odpowiedzi aeosynth ?
Peter Mortensen

4

Długość obiektu możemy znaleźć, używając:

Object.values(myObject).length

4

Trochę późno do gry, ale dobrym sposobem na osiągnięcie tego (tylko IE9 +) jest zdefiniowanie magicznego gettera we właściwości length:

Object.defineProperty(Object.prototype, "length", {
    get: function () {
        return Object.keys(this).length;
    }
});

Możesz go po prostu użyć w następujący sposób:

var myObj = { 'key': 'value' };
myObj.length;

Dałbym 1.


1
Pomijając argumenty przeciwko modyfikacji prototypu, osobiście NIGDY nie spowodowałem błędu i jest to dla mnie jedna z mocnych stron JavaScript.
MacroMan

3

Poniżej znajduje się wersja odpowiedzi Jamesa Coglana w CoffeeScript dla tych, którzy porzucili prosty JavaScript :)

Object.size = (obj) ->
  size = 0
  size++ for own key of obj
  size

1
Prawdopodobnie chciałeś powiedzieć size++ for own key of obj( own keycukier składniowy w CoffeeScript). Używanie hasOwnPropertybezpośrednio z obiektu jest niebezpieczne, ponieważ psuje się, gdy obiekt faktycznie ma taką właściwość.
Konrad Borowski,

2
OP nie poprosił o wersję CoffeeScript, ani nie jest oznaczony jako taki. To nie jest prawidłowa odpowiedź na pytanie.
Francisco Hodge,
Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.