diff --git a/1-js/4-data-types/01-object/2-hello-object/solution.md b/1-js/4-object-basics/01-object/2-hello-object/solution.md similarity index 100% rename from 1-js/4-data-types/01-object/2-hello-object/solution.md rename to 1-js/4-object-basics/01-object/2-hello-object/solution.md diff --git a/1-js/4-data-types/01-object/2-hello-object/task.md b/1-js/4-object-basics/01-object/2-hello-object/task.md similarity index 100% rename from 1-js/4-data-types/01-object/2-hello-object/task.md rename to 1-js/4-object-basics/01-object/2-hello-object/task.md diff --git a/1-js/4-data-types/01-object/3-is-empty/_js.view/solution.js b/1-js/4-object-basics/01-object/3-is-empty/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/01-object/3-is-empty/_js.view/solution.js rename to 1-js/4-object-basics/01-object/3-is-empty/_js.view/solution.js diff --git a/1-js/4-data-types/01-object/3-is-empty/_js.view/test.js b/1-js/4-object-basics/01-object/3-is-empty/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/01-object/3-is-empty/_js.view/test.js rename to 1-js/4-object-basics/01-object/3-is-empty/_js.view/test.js diff --git a/1-js/4-data-types/01-object/3-is-empty/solution.md b/1-js/4-object-basics/01-object/3-is-empty/solution.md similarity index 100% rename from 1-js/4-data-types/01-object/3-is-empty/solution.md rename to 1-js/4-object-basics/01-object/3-is-empty/solution.md diff --git a/1-js/4-data-types/01-object/3-is-empty/task.md b/1-js/4-object-basics/01-object/3-is-empty/task.md similarity index 100% rename from 1-js/4-data-types/01-object/3-is-empty/task.md rename to 1-js/4-object-basics/01-object/3-is-empty/task.md diff --git a/1-js/4-data-types/01-object/4-sum-object/solution.md b/1-js/4-object-basics/01-object/4-sum-object/solution.md similarity index 100% rename from 1-js/4-data-types/01-object/4-sum-object/solution.md rename to 1-js/4-object-basics/01-object/4-sum-object/solution.md diff --git a/1-js/4-data-types/01-object/4-sum-object/task.md b/1-js/4-object-basics/01-object/4-sum-object/task.md similarity index 100% rename from 1-js/4-data-types/01-object/4-sum-object/task.md rename to 1-js/4-object-basics/01-object/4-sum-object/task.md diff --git a/1-js/4-data-types/01-object/8-multiply-numeric/_js.view/solution.js b/1-js/4-object-basics/01-object/8-multiply-numeric/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/01-object/8-multiply-numeric/_js.view/solution.js rename to 1-js/4-object-basics/01-object/8-multiply-numeric/_js.view/solution.js diff --git a/1-js/4-data-types/01-object/8-multiply-numeric/_js.view/source.js b/1-js/4-object-basics/01-object/8-multiply-numeric/_js.view/source.js similarity index 100% rename from 1-js/4-data-types/01-object/8-multiply-numeric/_js.view/source.js rename to 1-js/4-object-basics/01-object/8-multiply-numeric/_js.view/source.js diff --git a/1-js/4-data-types/01-object/8-multiply-numeric/_js.view/test.js b/1-js/4-object-basics/01-object/8-multiply-numeric/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/01-object/8-multiply-numeric/_js.view/test.js rename to 1-js/4-object-basics/01-object/8-multiply-numeric/_js.view/test.js diff --git a/1-js/4-data-types/01-object/8-multiply-numeric/solution.md b/1-js/4-object-basics/01-object/8-multiply-numeric/solution.md similarity index 100% rename from 1-js/4-data-types/01-object/8-multiply-numeric/solution.md rename to 1-js/4-object-basics/01-object/8-multiply-numeric/solution.md diff --git a/1-js/4-data-types/01-object/8-multiply-numeric/task.md b/1-js/4-object-basics/01-object/8-multiply-numeric/task.md similarity index 100% rename from 1-js/4-data-types/01-object/8-multiply-numeric/task.md rename to 1-js/4-object-basics/01-object/8-multiply-numeric/task.md diff --git a/1-js/4-data-types/01-object/article.md b/1-js/4-object-basics/01-object/article.md similarity index 100% rename from 1-js/4-data-types/01-object/article.md rename to 1-js/4-object-basics/01-object/article.md diff --git a/1-js/4-data-types/01-object/object-user-delete.png b/1-js/4-object-basics/01-object/object-user-delete.png similarity index 100% rename from 1-js/4-data-types/01-object/object-user-delete.png rename to 1-js/4-object-basics/01-object/object-user-delete.png diff --git a/1-js/4-data-types/01-object/object-user-delete@2x.png b/1-js/4-object-basics/01-object/object-user-delete@2x.png similarity index 100% rename from 1-js/4-data-types/01-object/object-user-delete@2x.png rename to 1-js/4-object-basics/01-object/object-user-delete@2x.png diff --git a/1-js/4-data-types/01-object/object-user-empty.png b/1-js/4-object-basics/01-object/object-user-empty.png similarity index 100% rename from 1-js/4-data-types/01-object/object-user-empty.png rename to 1-js/4-object-basics/01-object/object-user-empty.png diff --git a/1-js/4-data-types/01-object/object-user-empty@2x.png b/1-js/4-object-basics/01-object/object-user-empty@2x.png similarity index 100% rename from 1-js/4-data-types/01-object/object-user-empty@2x.png rename to 1-js/4-object-basics/01-object/object-user-empty@2x.png diff --git a/1-js/4-data-types/01-object/object-user-isadmin.png b/1-js/4-object-basics/01-object/object-user-isadmin.png similarity index 100% rename from 1-js/4-data-types/01-object/object-user-isadmin.png rename to 1-js/4-object-basics/01-object/object-user-isadmin.png diff --git a/1-js/4-data-types/01-object/object-user-isadmin@2x.png b/1-js/4-object-basics/01-object/object-user-isadmin@2x.png similarity index 100% rename from 1-js/4-data-types/01-object/object-user-isadmin@2x.png rename to 1-js/4-object-basics/01-object/object-user-isadmin@2x.png diff --git a/1-js/4-data-types/01-object/object-user-props.png b/1-js/4-object-basics/01-object/object-user-props.png similarity index 100% rename from 1-js/4-data-types/01-object/object-user-props.png rename to 1-js/4-object-basics/01-object/object-user-props.png diff --git a/1-js/4-data-types/01-object/object-user-props@2x.png b/1-js/4-object-basics/01-object/object-user-props@2x.png similarity index 100% rename from 1-js/4-data-types/01-object/object-user-props@2x.png rename to 1-js/4-object-basics/01-object/object-user-props@2x.png diff --git a/1-js/4-data-types/01-object/object-user.png b/1-js/4-object-basics/01-object/object-user.png similarity index 100% rename from 1-js/4-data-types/01-object/object-user.png rename to 1-js/4-object-basics/01-object/object-user.png diff --git a/1-js/4-data-types/01-object/object-user@2x.png b/1-js/4-object-basics/01-object/object-user@2x.png similarity index 100% rename from 1-js/4-data-types/01-object/object-user@2x.png rename to 1-js/4-object-basics/01-object/object-user@2x.png diff --git a/1-js/4-data-types/01-object/object.png b/1-js/4-object-basics/01-object/object.png similarity index 100% rename from 1-js/4-data-types/01-object/object.png rename to 1-js/4-object-basics/01-object/object.png diff --git a/1-js/4-data-types/01-object/object@2x.png b/1-js/4-object-basics/01-object/object@2x.png similarity index 100% rename from 1-js/4-data-types/01-object/object@2x.png rename to 1-js/4-object-basics/01-object/object@2x.png diff --git a/1-js/4-data-types/01-object/variable-contains-reference.png b/1-js/4-object-basics/01-object/variable-contains-reference.png similarity index 100% rename from 1-js/4-data-types/01-object/variable-contains-reference.png rename to 1-js/4-object-basics/01-object/variable-contains-reference.png diff --git a/1-js/4-data-types/01-object/variable-contains-reference@2x.png b/1-js/4-object-basics/01-object/variable-contains-reference@2x.png similarity index 100% rename from 1-js/4-data-types/01-object/variable-contains-reference@2x.png rename to 1-js/4-object-basics/01-object/variable-contains-reference@2x.png diff --git a/1-js/4-data-types/01-object/variable-copy-reference.png b/1-js/4-object-basics/01-object/variable-copy-reference.png similarity index 100% rename from 1-js/4-data-types/01-object/variable-copy-reference.png rename to 1-js/4-object-basics/01-object/variable-copy-reference.png diff --git a/1-js/4-data-types/01-object/variable-copy-reference@2x.png b/1-js/4-object-basics/01-object/variable-copy-reference@2x.png similarity index 100% rename from 1-js/4-data-types/01-object/variable-copy-reference@2x.png rename to 1-js/4-object-basics/01-object/variable-copy-reference@2x.png diff --git a/1-js/4-data-types/01-object/variable-copy-value.png b/1-js/4-object-basics/01-object/variable-copy-value.png similarity index 100% rename from 1-js/4-data-types/01-object/variable-copy-value.png rename to 1-js/4-object-basics/01-object/variable-copy-value.png diff --git a/1-js/4-data-types/01-object/variable-copy-value@2x.png b/1-js/4-object-basics/01-object/variable-copy-value@2x.png similarity index 100% rename from 1-js/4-data-types/01-object/variable-copy-value@2x.png rename to 1-js/4-object-basics/01-object/variable-copy-value@2x.png diff --git a/1-js/4-data-types/02-garbage-collection/article.md b/1-js/4-object-basics/02-garbage-collection/article.md similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/article.md rename to 1-js/4-object-basics/02-garbage-collection/article.md diff --git a/1-js/4-data-types/02-garbage-collection/family-delete-refs.png b/1-js/4-object-basics/02-garbage-collection/family-delete-refs.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/family-delete-refs.png rename to 1-js/4-object-basics/02-garbage-collection/family-delete-refs.png diff --git a/1-js/4-data-types/02-garbage-collection/family-delete-refs@2x.png b/1-js/4-object-basics/02-garbage-collection/family-delete-refs@2x.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/family-delete-refs@2x.png rename to 1-js/4-object-basics/02-garbage-collection/family-delete-refs@2x.png diff --git a/1-js/4-data-types/02-garbage-collection/family-no-family.png b/1-js/4-object-basics/02-garbage-collection/family-no-family.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/family-no-family.png rename to 1-js/4-object-basics/02-garbage-collection/family-no-family.png diff --git a/1-js/4-data-types/02-garbage-collection/family-no-family@2x.png b/1-js/4-object-basics/02-garbage-collection/family-no-family@2x.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/family-no-family@2x.png rename to 1-js/4-object-basics/02-garbage-collection/family-no-family@2x.png diff --git a/1-js/4-data-types/02-garbage-collection/family-no-father-2.png b/1-js/4-object-basics/02-garbage-collection/family-no-father-2.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/family-no-father-2.png rename to 1-js/4-object-basics/02-garbage-collection/family-no-father-2.png diff --git a/1-js/4-data-types/02-garbage-collection/family-no-father-2@2x.png b/1-js/4-object-basics/02-garbage-collection/family-no-father-2@2x.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/family-no-father-2@2x.png rename to 1-js/4-object-basics/02-garbage-collection/family-no-father-2@2x.png diff --git a/1-js/4-data-types/02-garbage-collection/family-no-father.png b/1-js/4-object-basics/02-garbage-collection/family-no-father.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/family-no-father.png rename to 1-js/4-object-basics/02-garbage-collection/family-no-father.png diff --git a/1-js/4-data-types/02-garbage-collection/family-no-father@2x.png b/1-js/4-object-basics/02-garbage-collection/family-no-father@2x.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/family-no-father@2x.png rename to 1-js/4-object-basics/02-garbage-collection/family-no-father@2x.png diff --git a/1-js/4-data-types/02-garbage-collection/family.png b/1-js/4-object-basics/02-garbage-collection/family.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/family.png rename to 1-js/4-object-basics/02-garbage-collection/family.png diff --git a/1-js/4-data-types/02-garbage-collection/family@2x.png b/1-js/4-object-basics/02-garbage-collection/family@2x.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/family@2x.png rename to 1-js/4-object-basics/02-garbage-collection/family@2x.png diff --git a/1-js/4-data-types/02-garbage-collection/garbage-collection-1.png b/1-js/4-object-basics/02-garbage-collection/garbage-collection-1.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/garbage-collection-1.png rename to 1-js/4-object-basics/02-garbage-collection/garbage-collection-1.png diff --git a/1-js/4-data-types/02-garbage-collection/garbage-collection-1@2x.png b/1-js/4-object-basics/02-garbage-collection/garbage-collection-1@2x.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/garbage-collection-1@2x.png rename to 1-js/4-object-basics/02-garbage-collection/garbage-collection-1@2x.png diff --git a/1-js/4-data-types/02-garbage-collection/garbage-collection-2.png b/1-js/4-object-basics/02-garbage-collection/garbage-collection-2.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/garbage-collection-2.png rename to 1-js/4-object-basics/02-garbage-collection/garbage-collection-2.png diff --git a/1-js/4-data-types/02-garbage-collection/garbage-collection-2@2x.png b/1-js/4-object-basics/02-garbage-collection/garbage-collection-2@2x.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/garbage-collection-2@2x.png rename to 1-js/4-object-basics/02-garbage-collection/garbage-collection-2@2x.png diff --git a/1-js/4-data-types/02-garbage-collection/garbage-collection-3.png b/1-js/4-object-basics/02-garbage-collection/garbage-collection-3.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/garbage-collection-3.png rename to 1-js/4-object-basics/02-garbage-collection/garbage-collection-3.png diff --git a/1-js/4-data-types/02-garbage-collection/garbage-collection-3@2x.png b/1-js/4-object-basics/02-garbage-collection/garbage-collection-3@2x.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/garbage-collection-3@2x.png rename to 1-js/4-object-basics/02-garbage-collection/garbage-collection-3@2x.png diff --git a/1-js/4-data-types/02-garbage-collection/garbage-collection-4.png b/1-js/4-object-basics/02-garbage-collection/garbage-collection-4.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/garbage-collection-4.png rename to 1-js/4-object-basics/02-garbage-collection/garbage-collection-4.png diff --git a/1-js/4-data-types/02-garbage-collection/garbage-collection-4@2x.png b/1-js/4-object-basics/02-garbage-collection/garbage-collection-4@2x.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/garbage-collection-4@2x.png rename to 1-js/4-object-basics/02-garbage-collection/garbage-collection-4@2x.png diff --git a/1-js/4-data-types/02-garbage-collection/garbage-collection-5.png b/1-js/4-object-basics/02-garbage-collection/garbage-collection-5.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/garbage-collection-5.png rename to 1-js/4-object-basics/02-garbage-collection/garbage-collection-5.png diff --git a/1-js/4-data-types/02-garbage-collection/garbage-collection-5@2x.png b/1-js/4-object-basics/02-garbage-collection/garbage-collection-5@2x.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/garbage-collection-5@2x.png rename to 1-js/4-object-basics/02-garbage-collection/garbage-collection-5@2x.png diff --git a/1-js/4-data-types/02-garbage-collection/garbage-collection.png b/1-js/4-object-basics/02-garbage-collection/garbage-collection.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/garbage-collection.png rename to 1-js/4-object-basics/02-garbage-collection/garbage-collection.png diff --git a/1-js/4-data-types/02-garbage-collection/garbage-collection@2x.png b/1-js/4-object-basics/02-garbage-collection/garbage-collection@2x.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/garbage-collection@2x.png rename to 1-js/4-object-basics/02-garbage-collection/garbage-collection@2x.png diff --git a/1-js/4-data-types/02-garbage-collection/memory-user-john-admin.png b/1-js/4-object-basics/02-garbage-collection/memory-user-john-admin.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/memory-user-john-admin.png rename to 1-js/4-object-basics/02-garbage-collection/memory-user-john-admin.png diff --git a/1-js/4-data-types/02-garbage-collection/memory-user-john-admin@2x.png b/1-js/4-object-basics/02-garbage-collection/memory-user-john-admin@2x.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/memory-user-john-admin@2x.png rename to 1-js/4-object-basics/02-garbage-collection/memory-user-john-admin@2x.png diff --git a/1-js/4-data-types/02-garbage-collection/memory-user-john-lost.png b/1-js/4-object-basics/02-garbage-collection/memory-user-john-lost.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/memory-user-john-lost.png rename to 1-js/4-object-basics/02-garbage-collection/memory-user-john-lost.png diff --git a/1-js/4-data-types/02-garbage-collection/memory-user-john-lost@2x.png b/1-js/4-object-basics/02-garbage-collection/memory-user-john-lost@2x.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/memory-user-john-lost@2x.png rename to 1-js/4-object-basics/02-garbage-collection/memory-user-john-lost@2x.png diff --git a/1-js/4-data-types/02-garbage-collection/memory-user-john.png b/1-js/4-object-basics/02-garbage-collection/memory-user-john.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/memory-user-john.png rename to 1-js/4-object-basics/02-garbage-collection/memory-user-john.png diff --git a/1-js/4-data-types/02-garbage-collection/memory-user-john@2x.png b/1-js/4-object-basics/02-garbage-collection/memory-user-john@2x.png similarity index 100% rename from 1-js/4-data-types/02-garbage-collection/memory-user-john@2x.png rename to 1-js/4-object-basics/02-garbage-collection/memory-user-john@2x.png diff --git a/1-js/4-data-types/03-object-methods/2-check-syntax/solution.md b/1-js/4-object-basics/03-object-methods/2-check-syntax/solution.md similarity index 100% rename from 1-js/4-data-types/03-object-methods/2-check-syntax/solution.md rename to 1-js/4-object-basics/03-object-methods/2-check-syntax/solution.md diff --git a/1-js/4-data-types/03-object-methods/2-check-syntax/task.md b/1-js/4-object-basics/03-object-methods/2-check-syntax/task.md similarity index 100% rename from 1-js/4-data-types/03-object-methods/2-check-syntax/task.md rename to 1-js/4-object-basics/03-object-methods/2-check-syntax/task.md diff --git a/1-js/4-data-types/03-object-methods/3-why-this/solution.md b/1-js/4-object-basics/03-object-methods/3-why-this/solution.md similarity index 100% rename from 1-js/4-data-types/03-object-methods/3-why-this/solution.md rename to 1-js/4-object-basics/03-object-methods/3-why-this/solution.md diff --git a/1-js/4-data-types/03-object-methods/3-why-this/task.md b/1-js/4-object-basics/03-object-methods/3-why-this/task.md similarity index 100% rename from 1-js/4-data-types/03-object-methods/3-why-this/task.md rename to 1-js/4-object-basics/03-object-methods/3-why-this/task.md diff --git a/1-js/4-data-types/03-object-methods/4-object-property-this/solution.md b/1-js/4-object-basics/03-object-methods/4-object-property-this/solution.md similarity index 100% rename from 1-js/4-data-types/03-object-methods/4-object-property-this/solution.md rename to 1-js/4-object-basics/03-object-methods/4-object-property-this/solution.md diff --git a/1-js/4-data-types/03-object-methods/4-object-property-this/task.md b/1-js/4-object-basics/03-object-methods/4-object-property-this/task.md similarity index 100% rename from 1-js/4-data-types/03-object-methods/4-object-property-this/task.md rename to 1-js/4-object-basics/03-object-methods/4-object-property-this/task.md diff --git a/1-js/4-data-types/03-object-methods/7-calculator/_js.view/solution.js b/1-js/4-object-basics/03-object-methods/7-calculator/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/03-object-methods/7-calculator/_js.view/solution.js rename to 1-js/4-object-basics/03-object-methods/7-calculator/_js.view/solution.js diff --git a/1-js/4-data-types/03-object-methods/7-calculator/_js.view/test.js b/1-js/4-object-basics/03-object-methods/7-calculator/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/03-object-methods/7-calculator/_js.view/test.js rename to 1-js/4-object-basics/03-object-methods/7-calculator/_js.view/test.js diff --git a/1-js/4-data-types/03-object-methods/7-calculator/solution.md b/1-js/4-object-basics/03-object-methods/7-calculator/solution.md similarity index 100% rename from 1-js/4-data-types/03-object-methods/7-calculator/solution.md rename to 1-js/4-object-basics/03-object-methods/7-calculator/solution.md diff --git a/1-js/4-data-types/03-object-methods/7-calculator/task.md b/1-js/4-object-basics/03-object-methods/7-calculator/task.md similarity index 100% rename from 1-js/4-data-types/03-object-methods/7-calculator/task.md rename to 1-js/4-object-basics/03-object-methods/7-calculator/task.md diff --git a/1-js/4-data-types/03-object-methods/8-chain-calls/solution.md b/1-js/4-object-basics/03-object-methods/8-chain-calls/solution.md similarity index 100% rename from 1-js/4-data-types/03-object-methods/8-chain-calls/solution.md rename to 1-js/4-object-basics/03-object-methods/8-chain-calls/solution.md diff --git a/1-js/4-data-types/03-object-methods/8-chain-calls/task.md b/1-js/4-object-basics/03-object-methods/8-chain-calls/task.md similarity index 100% rename from 1-js/4-data-types/03-object-methods/8-chain-calls/task.md rename to 1-js/4-object-basics/03-object-methods/8-chain-calls/task.md diff --git a/1-js/4-data-types/03-object-methods/9-string-new-property/solution.md b/1-js/4-object-basics/03-object-methods/9-string-new-property/solution.md similarity index 100% rename from 1-js/4-data-types/03-object-methods/9-string-new-property/solution.md rename to 1-js/4-object-basics/03-object-methods/9-string-new-property/solution.md diff --git a/1-js/4-data-types/03-object-methods/9-string-new-property/task.md b/1-js/4-object-basics/03-object-methods/9-string-new-property/task.md similarity index 100% rename from 1-js/4-data-types/03-object-methods/9-string-new-property/task.md rename to 1-js/4-object-basics/03-object-methods/9-string-new-property/task.md diff --git a/1-js/4-data-types/03-object-methods/article.md b/1-js/4-object-basics/03-object-methods/article.md similarity index 100% rename from 1-js/4-data-types/03-object-methods/article.md rename to 1-js/4-object-basics/03-object-methods/article.md diff --git a/1-js/4-data-types/07-primitives-methods/1-string-new-property/solution.md b/1-js/4-object-basics/04-primitives-methods/1-string-new-property/solution.md similarity index 100% rename from 1-js/4-data-types/07-primitives-methods/1-string-new-property/solution.md rename to 1-js/4-object-basics/04-primitives-methods/1-string-new-property/solution.md diff --git a/1-js/4-data-types/07-primitives-methods/1-string-new-property/task.md b/1-js/4-object-basics/04-primitives-methods/1-string-new-property/task.md similarity index 100% rename from 1-js/4-data-types/07-primitives-methods/1-string-new-property/task.md rename to 1-js/4-object-basics/04-primitives-methods/1-string-new-property/task.md diff --git a/1-js/4-data-types/07-primitives-methods/article.md b/1-js/4-object-basics/04-primitives-methods/article.md similarity index 92% rename from 1-js/4-data-types/07-primitives-methods/article.md rename to 1-js/4-object-basics/04-primitives-methods/article.md index 68beebf4..a38e14c1 100644 --- a/1-js/4-data-types/07-primitives-methods/article.md +++ b/1-js/4-object-basics/04-primitives-methods/article.md @@ -1,10 +1,10 @@ # Methods of primitives -JavaScript allows to work with primitives (strings, numbers etc) as if they were objects. They have methods and such. Of course, primitives are not objects (and here we plan to make it even more clear), but can be used like them. +JavaScript allows to work with primitives (strings, numbers etc) as if they were objects. They also have methods and such. Of course, primitives are not objects (and here we plan to make it even more clear), but can be used like them. [cut] -Let's formulate the definitive distinction between primitives and objects. +Let's formulate the key distinction between primitives and objects. A primitive : Is a value of a primitive type. There are 6 primitive types: `string`, `number`, `boolean`, `symbol`, `null` and `undefined`. @@ -77,7 +77,7 @@ let n = 1.23456; alert( n.toFixed(2) ); // 1.23 ``` -We'll see more specific methods in next chapters. +We'll see more specific methods in chapters and . ````warn header="null/undefined have no methods" Special primitives `null` and `undefined` are exceptions. They have no corresponding "wrapper objects" and provide no methods. In a sense, they are "the most primitive". diff --git a/1-js/4-data-types/04-constructor-new/1-two-functions-one-object/solution.md b/1-js/4-object-basics/05-constructor-new/1-two-functions-one-object/solution.md similarity index 100% rename from 1-js/4-data-types/04-constructor-new/1-two-functions-one-object/solution.md rename to 1-js/4-object-basics/05-constructor-new/1-two-functions-one-object/solution.md diff --git a/1-js/4-data-types/04-constructor-new/1-two-functions-one-object/task.md b/1-js/4-object-basics/05-constructor-new/1-two-functions-one-object/task.md similarity index 100% rename from 1-js/4-data-types/04-constructor-new/1-two-functions-one-object/task.md rename to 1-js/4-object-basics/05-constructor-new/1-two-functions-one-object/task.md diff --git a/1-js/4-data-types/04-constructor-new/2-calculator-constructor/_js.view/solution.js b/1-js/4-object-basics/05-constructor-new/2-calculator-constructor/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/04-constructor-new/2-calculator-constructor/_js.view/solution.js rename to 1-js/4-object-basics/05-constructor-new/2-calculator-constructor/_js.view/solution.js diff --git a/1-js/4-data-types/04-constructor-new/2-calculator-constructor/_js.view/test.js b/1-js/4-object-basics/05-constructor-new/2-calculator-constructor/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/04-constructor-new/2-calculator-constructor/_js.view/test.js rename to 1-js/4-object-basics/05-constructor-new/2-calculator-constructor/_js.view/test.js diff --git a/1-js/4-data-types/04-constructor-new/2-calculator-constructor/solution.md b/1-js/4-object-basics/05-constructor-new/2-calculator-constructor/solution.md similarity index 100% rename from 1-js/4-data-types/04-constructor-new/2-calculator-constructor/solution.md rename to 1-js/4-object-basics/05-constructor-new/2-calculator-constructor/solution.md diff --git a/1-js/4-data-types/04-constructor-new/2-calculator-constructor/task.md b/1-js/4-object-basics/05-constructor-new/2-calculator-constructor/task.md similarity index 100% rename from 1-js/4-data-types/04-constructor-new/2-calculator-constructor/task.md rename to 1-js/4-object-basics/05-constructor-new/2-calculator-constructor/task.md diff --git a/1-js/4-data-types/04-constructor-new/3-accumulator/_js.view/solution.js b/1-js/4-object-basics/05-constructor-new/3-accumulator/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/04-constructor-new/3-accumulator/_js.view/solution.js rename to 1-js/4-object-basics/05-constructor-new/3-accumulator/_js.view/solution.js diff --git a/1-js/4-data-types/04-constructor-new/3-accumulator/_js.view/test.js b/1-js/4-object-basics/05-constructor-new/3-accumulator/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/04-constructor-new/3-accumulator/_js.view/test.js rename to 1-js/4-object-basics/05-constructor-new/3-accumulator/_js.view/test.js diff --git a/1-js/4-data-types/04-constructor-new/3-accumulator/solution.md b/1-js/4-object-basics/05-constructor-new/3-accumulator/solution.md similarity index 100% rename from 1-js/4-data-types/04-constructor-new/3-accumulator/solution.md rename to 1-js/4-object-basics/05-constructor-new/3-accumulator/solution.md diff --git a/1-js/4-data-types/04-constructor-new/3-accumulator/task.md b/1-js/4-object-basics/05-constructor-new/3-accumulator/task.md similarity index 100% rename from 1-js/4-data-types/04-constructor-new/3-accumulator/task.md rename to 1-js/4-object-basics/05-constructor-new/3-accumulator/task.md diff --git a/1-js/4-data-types/04-constructor-new/4-calculator-extendable/_js.view/solution.js b/1-js/4-object-basics/05-constructor-new/4-calculator-extendable/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/04-constructor-new/4-calculator-extendable/_js.view/solution.js rename to 1-js/4-object-basics/05-constructor-new/4-calculator-extendable/_js.view/solution.js diff --git a/1-js/4-data-types/04-constructor-new/4-calculator-extendable/_js.view/test.js b/1-js/4-object-basics/05-constructor-new/4-calculator-extendable/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/04-constructor-new/4-calculator-extendable/_js.view/test.js rename to 1-js/4-object-basics/05-constructor-new/4-calculator-extendable/_js.view/test.js diff --git a/1-js/4-data-types/04-constructor-new/4-calculator-extendable/solution.md b/1-js/4-object-basics/05-constructor-new/4-calculator-extendable/solution.md similarity index 100% rename from 1-js/4-data-types/04-constructor-new/4-calculator-extendable/solution.md rename to 1-js/4-object-basics/05-constructor-new/4-calculator-extendable/solution.md diff --git a/1-js/4-data-types/04-constructor-new/4-calculator-extendable/task.md b/1-js/4-object-basics/05-constructor-new/4-calculator-extendable/task.md similarity index 100% rename from 1-js/4-data-types/04-constructor-new/4-calculator-extendable/task.md rename to 1-js/4-object-basics/05-constructor-new/4-calculator-extendable/task.md diff --git a/1-js/4-data-types/04-constructor-new/article.md b/1-js/4-object-basics/05-constructor-new/article.md similarity index 100% rename from 1-js/4-data-types/04-constructor-new/article.md rename to 1-js/4-object-basics/05-constructor-new/article.md diff --git a/1-js/4-data-types/05-symbol/article.md b/1-js/4-object-basics/06-symbol/article.md similarity index 77% rename from 1-js/4-data-types/05-symbol/article.md rename to 1-js/4-object-basics/06-symbol/article.md index c4252452..fc8c1b0b 100644 --- a/1-js/4-data-types/05-symbol/article.md +++ b/1-js/4-object-basics/06-symbol/article.md @@ -31,7 +31,7 @@ alert(id1 == id2); // false */!* ``` -If you are familiar with Ruby or another language that uses the "symbol" concept -- please don't be misguided. Javascript symbols are pretty different. +If you are familiar with Ruby or another language that also has some sort of "symbols" -- please don't be misguided. Javascript symbols are different. ## "Private" properties @@ -155,11 +155,11 @@ alert( obj[0] ); // test (same property) Normally, all symbols are different. But sometimes we want same-named symbols to be the same. -For instance, different parts of our application want to use `Symbol("id")` meaning the exactly the same property. +For instance, different parts of our application want to access symbol `"id"` meaning the exactly the same property. -To achieve that, there's a *global symbol registry*. That's a place where we can create symbols and access them later, and it is guaranteed that repeating access by the same name returns the same symbol. +To achieve that, there exists a *global symbol registry*. We can create symbols in it and and access them later, and it guarantees that repeated accesses by the same name return exactly the same symbol. -To can create or read a symbol, use `Symbol.for(name)`. +To can create or read a symbol in the registry, use `Symbol.for(name)`. For instance: @@ -174,17 +174,17 @@ let nameAgain = Symbol.for("name"); alert( name === nameAgain ); // true ``` -If we want an application-wide symbol, accessible everywhere in the code -- that's what the registry is for. +Symbols inside the registry are called *global symbols*. If we want an application-wide symbol, accessible everywhere in the code -- that's what they are for. ```smart header="That sounds like Ruby" In some programming languages, like Ruby, there's a single symbol per name. -In Javascript, as we can see, it's correct for global symbols. +In Javascript, as we can see, that's right for global symbols. ``` ### Symbol.keyFor -For global symbols, not only `Symbol.for(name)` returns a symbol by name, but there's a reverse call: `Symbol.keyFor(sym)`, that returns a name for a global symbol. +For global symbols, not only `Symbol.for(name)` returns a symbol by name, but there's a reverse call: `Symbol.keyFor(sym)`, that does the reverse: returns a name by a global symbol. For instance: @@ -197,9 +197,7 @@ alert( Symbol.keyFor(sym) ); // name alert( Symbol.keyFor(sym2) ); // id ``` -The `Symbol.keyFor` internally uses the global symbol registry, to look up the name for the symbol. - -So it doesn't work for non-global symbols. If the symbol is not global, it returns `undefined. +The `Symbol.keyFor` internally uses the global symbol registry to look up the name for the symbol. So it doesn't work for non-global symbols. If the symbol is not global, it won't be able to find it and return `undefined`. For instance: @@ -215,18 +213,27 @@ For non-global symbols, the name is only used for debugging purposes. There exist many "system" symbols that Javascript uses internally, and we can use them to fine-tune various aspects of our objects. -They are listed in the specification in the [Well-known symbols](https://tc39.github.io/ecma262/#sec-well-known-symbols) table. For instance, `Symbol.toPrimitive` allows to describe object to primitive conversion. We'll see its use very soon. Other symbols will become more obvious as we'll study the corresponding language features. +They are listed in the specification in the [Well-known symbols](https://tc39.github.io/ecma262/#sec-well-known-symbols) table: + +- `Symbol.hasInstance` +- `Symbol.isConcatSpreadable` +- `Symbol.iterator` +- `Symbol.toPrimitive` +- ...and so on. + +For instance, `Symbol.toPrimitive` allows to describe object to primitive conversion. We'll see its use very soon. + +Other symbols will also become familiar when we study the corresponding language features. ## Summary - Symbol is a primitive type for unique identifiers. - Symbols are created with `Symbol(name)` call. - Symbols are useful if we want to create a field that only those who know the symbol can access. +- Symbols don't appear in `for..in` loops. - Symbols created with `Symbol(name)` are always different, even if they have the same name. If we want same-named symbols to be equal, then we should use the global registry: `Symbol.for(name)` returns (creates if needed) a global symbol with the given name. Multiple calls return the same symbol. - There are system symbols used by Javascript and accessible as `Symbol.*`. We can use them to alter some built-in behaviors. -Symbols don't appear in `for..in` loops. As we'll see further, there are other means to get object properties which also ignore symbols, so they remain hidden. - -Technically though, there is still a way to discover all symbols of an object with a build-in method [Object.getOwnPropertySymbols(obj)](mdn:js/Object/getOwnPropertySymbols). Also there is a method named [Reflect.ownKeys(obj)](mdn:js/Reflect/ownKeys) that returns all keys of an object, including symbolic ones. So they are not completely hidden and private. +Technically, symbols are not 100% hidden. There is a build-in method [Object.getOwnPropertySymbols(obj)](mdn:js/Object/getOwnPropertySymbols) that allows to get all symbols. Also there is a method named [Reflect.ownKeys(obj)](mdn:js/Reflect/ownKeys) that returns *all* keys of an object including symbolic ones. So they are not completely hidden and private. But most libraries, built-in methods and syntax constructs adhere to a common agreement that they are. And the one who explicitly calls the aforementioned methods probably understands well what he's doing. \ No newline at end of file diff --git a/1-js/4-data-types/06-object-toprimitive/article.md b/1-js/4-object-basics/07-object-toprimitive/article.md similarity index 77% rename from 1-js/4-data-types/06-object-toprimitive/article.md rename to 1-js/4-object-basics/07-object-toprimitive/article.md index 647df253..fe005534 100644 --- a/1-js/4-data-types/06-object-toprimitive/article.md +++ b/1-js/4-object-basics/07-object-toprimitive/article.md @@ -14,15 +14,15 @@ The process of object to primitive conversion can be customized, here we'll see The conversion of an object to primitive value (a number or a string) is a rare thing in practice. -Just think about cases when such conversion may be necessary. For instance, numeric conversion happens when we compare an object against a primitive: `user == 18`. But what such comparison actually means? Are we going to compare `18` against user's age? Then it would be more obvious to write `user.age == 18`? And it's easier to read it too. +Just think about cases when such conversion may be necessary. For instance, numeric conversion happens when we compare an object against a primitive: `user > 18`. But what such comparison actually means? Are we going to compare `18` against user's age? Then it would be more obvious to write `user.age > 18`. And it's easier to read and understand it too. -Or, for a string conversion... Where does it happen? Usually, when we output an object. But simple ways of object-as-string output like `alert(user)` are only used for debugging and logging purposes. In projects, the output is more complicated, we may need to tune it by additional parameters, so it should be implemented by special methods. +Or, for a string conversion... Where does it happen? Usually, when we output an object. But simple ways of object-as-string output like `alert(user)` are only used for debugging and logging purposes. For real stuff, the output is more complicated, we may need to provide it additional parameters. That's why we usually implement it using object methods like `user.format()` or even in more advanced ways. So, most of the time, it's more flexible and gives more readable code to explicitly write an object property or call a method than rely on the conversion. That said, there are still valid reasons why we should know how to-primitive conversion works. -- The object-as-string kind of output is still useful sometimes. Without a customized conversion it will show `[object Object]`. +- Simple object-as-string output may be useable sometimes. Without a customized conversion it will show `[object Object]`. - Many built-in objects implement their own to-primitive conversion, we plan to cover that. - Sometimes it just happens (on mistake?), and we should understand what's going on. - Okay, the final one. There are quizzes and questions on interviews that rely on that knowledge. Looks like people think it's a good sigh that person understands Javascript if he knows type conversions well. @@ -72,11 +72,11 @@ There are 3 types (also called "hints") of object-to-primitive conversion: if (user == 1) { ... }; ``` - Still, there's some inconsistency here. The greater/less operator `<>` can work with both strings and numbers, it compares them differently: dictionary order is used for strings. Still, it uses "number" hint. That's for historical reasons. + There's some inconsistency here. The greater/less operator `<>` can work with both strings and numbers, it compares them differently. Still, it uses "number" hint. That's for historical reasons. In practice, all built-in objects except for one case (`Date` object, we'll learn it later) implement `"default"` conversion the same way as `"number"`. And probably we should do the same. -Please note -- there's only three. That simple. There is no "boolean" (all objects are `true` in boolean context) or anything else. And if we treat `"default"` and `"number"` the same, like most builtins do, then there are only two conversions. Not many. +Please note -- there are only three conversions. That simple. There is no "boolean" (all objects are `true` in boolean context) or anything else. And if we treat `"default"` and `"number"` the same, like most built-ins do, then there are only two conversions. To do the conversion, Javascript tries to find and call these three object methods: @@ -140,7 +140,7 @@ alert(+user); // valueOf -> 1000 alert(user + 500); // valueOf -> 1500 ``` -In practice, we often want a single "catch-all" place to handle all primitive conversions. In this case we can implement `toString` only, like this: +Often we want a single "catch-all" place to handle all primitive conversions. In this case we can implement `toString` only, like this: ```js run let user = { @@ -155,6 +155,9 @@ alert(user); // toString -> John alert(user + 500); // toString -> John500 ``` +In the absense of `Symbol.toPrimitive` and `valueOf`, `toString` will handle all primitive conversions. + + ## ToPrimitive and ToString/ToNumber The important thing to know about all primitive-conversion methods is that they not necessarily return the "hinted" primitive. @@ -167,11 +170,11 @@ An operation that was the reason for the conversion gets that primitive, and the For instance: -- All mathematical operations except binary plus apply `ToNumber` +- All mathematical operations except binary plus apply `ToNumber`: ```js run let obj = { - toString() { // toString used for everything in the absense of other methods + toString() { // toString used for numeric conversion in the absense of valueOf return "2"; } }; @@ -179,8 +182,9 @@ For instance: alert(obj * 2); // 4 ``` -- Binary plus first checks if it's a string, and then does concatenation, otherwise performs `ToNumber` and works with numbers. +- Binary plus first checks if the primitive is a string, and then does concatenation, otherwise performs `ToNumber` and works with numbers. + String example: ```js run let obj = { toString() { @@ -188,9 +192,10 @@ For instance: } }; - alert(obj + 2); // 22 (string => concatenation) + alert(obj + 2); // 22 (ToPrimitive returned string => concatenation) ``` + Number example: ```js run let obj = { toString() { @@ -198,7 +203,7 @@ For instance: } }; - alert(obj + 2); // 3 (not string => ToNumber) + alert(obj + 2); // 3 (ToPrimitive returned boolean, not string => ToNumber) ``` ## Summary diff --git a/1-js/4-object-basics/index.md b/1-js/4-object-basics/index.md new file mode 100644 index 00000000..2ced68de --- /dev/null +++ b/1-js/4-object-basics/index.md @@ -0,0 +1,2 @@ +# Object basics + diff --git a/1-js/4-data-types/08-number/1-sum-interface/solution.md b/1-js/5-data-types/01-number/1-sum-interface/solution.md similarity index 100% rename from 1-js/4-data-types/08-number/1-sum-interface/solution.md rename to 1-js/5-data-types/01-number/1-sum-interface/solution.md diff --git a/1-js/4-data-types/08-number/1-sum-interface/task.md b/1-js/5-data-types/01-number/1-sum-interface/task.md similarity index 100% rename from 1-js/4-data-types/08-number/1-sum-interface/task.md rename to 1-js/5-data-types/01-number/1-sum-interface/task.md diff --git a/1-js/4-data-types/08-number/2-why-rounded-down/solution.md b/1-js/5-data-types/01-number/2-why-rounded-down/solution.md similarity index 100% rename from 1-js/4-data-types/08-number/2-why-rounded-down/solution.md rename to 1-js/5-data-types/01-number/2-why-rounded-down/solution.md diff --git a/1-js/4-data-types/08-number/2-why-rounded-down/task.md b/1-js/5-data-types/01-number/2-why-rounded-down/task.md similarity index 100% rename from 1-js/4-data-types/08-number/2-why-rounded-down/task.md rename to 1-js/5-data-types/01-number/2-why-rounded-down/task.md diff --git a/1-js/4-data-types/08-number/3-repeat-until-number/_js.view/solution.js b/1-js/5-data-types/01-number/3-repeat-until-number/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/08-number/3-repeat-until-number/_js.view/solution.js rename to 1-js/5-data-types/01-number/3-repeat-until-number/_js.view/solution.js diff --git a/1-js/4-data-types/08-number/3-repeat-until-number/_js.view/test.js b/1-js/5-data-types/01-number/3-repeat-until-number/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/08-number/3-repeat-until-number/_js.view/test.js rename to 1-js/5-data-types/01-number/3-repeat-until-number/_js.view/test.js diff --git a/1-js/4-data-types/08-number/3-repeat-until-number/solution.md b/1-js/5-data-types/01-number/3-repeat-until-number/solution.md similarity index 100% rename from 1-js/4-data-types/08-number/3-repeat-until-number/solution.md rename to 1-js/5-data-types/01-number/3-repeat-until-number/solution.md diff --git a/1-js/4-data-types/08-number/3-repeat-until-number/task.md b/1-js/5-data-types/01-number/3-repeat-until-number/task.md similarity index 100% rename from 1-js/4-data-types/08-number/3-repeat-until-number/task.md rename to 1-js/5-data-types/01-number/3-repeat-until-number/task.md diff --git a/1-js/4-data-types/08-number/4-endless-loop-error/solution.md b/1-js/5-data-types/01-number/4-endless-loop-error/solution.md similarity index 100% rename from 1-js/4-data-types/08-number/4-endless-loop-error/solution.md rename to 1-js/5-data-types/01-number/4-endless-loop-error/solution.md diff --git a/1-js/4-data-types/08-number/4-endless-loop-error/task.md b/1-js/5-data-types/01-number/4-endless-loop-error/task.md similarity index 100% rename from 1-js/4-data-types/08-number/4-endless-loop-error/task.md rename to 1-js/5-data-types/01-number/4-endless-loop-error/task.md diff --git a/1-js/4-data-types/08-number/8-random-min-max/solution.md b/1-js/5-data-types/01-number/8-random-min-max/solution.md similarity index 100% rename from 1-js/4-data-types/08-number/8-random-min-max/solution.md rename to 1-js/5-data-types/01-number/8-random-min-max/solution.md diff --git a/1-js/4-data-types/08-number/8-random-min-max/task.md b/1-js/5-data-types/01-number/8-random-min-max/task.md similarity index 100% rename from 1-js/4-data-types/08-number/8-random-min-max/task.md rename to 1-js/5-data-types/01-number/8-random-min-max/task.md diff --git a/1-js/4-data-types/08-number/9-random-int-min-max/solution.md b/1-js/5-data-types/01-number/9-random-int-min-max/solution.md similarity index 100% rename from 1-js/4-data-types/08-number/9-random-int-min-max/solution.md rename to 1-js/5-data-types/01-number/9-random-int-min-max/solution.md diff --git a/1-js/4-data-types/08-number/9-random-int-min-max/task.md b/1-js/5-data-types/01-number/9-random-int-min-max/task.md similarity index 100% rename from 1-js/4-data-types/08-number/9-random-int-min-max/task.md rename to 1-js/5-data-types/01-number/9-random-int-min-max/task.md diff --git a/1-js/4-data-types/08-number/article.md b/1-js/5-data-types/01-number/article.md similarity index 99% rename from 1-js/4-data-types/08-number/article.md rename to 1-js/5-data-types/01-number/article.md index af32d44c..1cf1bf5b 100644 --- a/1-js/4-data-types/08-number/article.md +++ b/1-js/5-data-types/01-number/article.md @@ -1,4 +1,4 @@ -# Numbers in-depth +# Numbers All numbers in JavaScript are stored in 64-bit format [IEEE-754](http://en.wikipedia.org/wiki/IEEE_754-1985) also known as "double precision". diff --git a/1-js/4-data-types/09-string/1-ucfirst/_js.view/solution.js b/1-js/5-data-types/02-string/1-ucfirst/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/09-string/1-ucfirst/_js.view/solution.js rename to 1-js/5-data-types/02-string/1-ucfirst/_js.view/solution.js diff --git a/1-js/4-data-types/09-string/1-ucfirst/_js.view/test.js b/1-js/5-data-types/02-string/1-ucfirst/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/09-string/1-ucfirst/_js.view/test.js rename to 1-js/5-data-types/02-string/1-ucfirst/_js.view/test.js diff --git a/1-js/4-data-types/09-string/1-ucfirst/solution.md b/1-js/5-data-types/02-string/1-ucfirst/solution.md similarity index 100% rename from 1-js/4-data-types/09-string/1-ucfirst/solution.md rename to 1-js/5-data-types/02-string/1-ucfirst/solution.md diff --git a/1-js/4-data-types/09-string/1-ucfirst/task.md b/1-js/5-data-types/02-string/1-ucfirst/task.md similarity index 100% rename from 1-js/4-data-types/09-string/1-ucfirst/task.md rename to 1-js/5-data-types/02-string/1-ucfirst/task.md diff --git a/1-js/4-data-types/09-string/2-check-spam/_js.view/solution.js b/1-js/5-data-types/02-string/2-check-spam/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/09-string/2-check-spam/_js.view/solution.js rename to 1-js/5-data-types/02-string/2-check-spam/_js.view/solution.js diff --git a/1-js/4-data-types/09-string/2-check-spam/_js.view/test.js b/1-js/5-data-types/02-string/2-check-spam/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/09-string/2-check-spam/_js.view/test.js rename to 1-js/5-data-types/02-string/2-check-spam/_js.view/test.js diff --git a/1-js/4-data-types/09-string/2-check-spam/solution.md b/1-js/5-data-types/02-string/2-check-spam/solution.md similarity index 100% rename from 1-js/4-data-types/09-string/2-check-spam/solution.md rename to 1-js/5-data-types/02-string/2-check-spam/solution.md diff --git a/1-js/4-data-types/09-string/2-check-spam/task.md b/1-js/5-data-types/02-string/2-check-spam/task.md similarity index 100% rename from 1-js/4-data-types/09-string/2-check-spam/task.md rename to 1-js/5-data-types/02-string/2-check-spam/task.md diff --git a/1-js/4-data-types/09-string/3-truncate/_js.view/solution.js b/1-js/5-data-types/02-string/3-truncate/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/09-string/3-truncate/_js.view/solution.js rename to 1-js/5-data-types/02-string/3-truncate/_js.view/solution.js diff --git a/1-js/4-data-types/09-string/3-truncate/_js.view/test.js b/1-js/5-data-types/02-string/3-truncate/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/09-string/3-truncate/_js.view/test.js rename to 1-js/5-data-types/02-string/3-truncate/_js.view/test.js diff --git a/1-js/4-data-types/09-string/3-truncate/solution.md b/1-js/5-data-types/02-string/3-truncate/solution.md similarity index 100% rename from 1-js/4-data-types/09-string/3-truncate/solution.md rename to 1-js/5-data-types/02-string/3-truncate/solution.md diff --git a/1-js/4-data-types/09-string/3-truncate/task.md b/1-js/5-data-types/02-string/3-truncate/task.md similarity index 100% rename from 1-js/4-data-types/09-string/3-truncate/task.md rename to 1-js/5-data-types/02-string/3-truncate/task.md diff --git a/1-js/4-data-types/09-string/4-extract-currency/_js.view/solution.js b/1-js/5-data-types/02-string/4-extract-currency/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/09-string/4-extract-currency/_js.view/solution.js rename to 1-js/5-data-types/02-string/4-extract-currency/_js.view/solution.js diff --git a/1-js/4-data-types/09-string/4-extract-currency/_js.view/test.js b/1-js/5-data-types/02-string/4-extract-currency/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/09-string/4-extract-currency/_js.view/test.js rename to 1-js/5-data-types/02-string/4-extract-currency/_js.view/test.js diff --git a/1-js/4-data-types/09-string/4-extract-currency/solution.md b/1-js/5-data-types/02-string/4-extract-currency/solution.md similarity index 100% rename from 1-js/4-data-types/09-string/4-extract-currency/solution.md rename to 1-js/5-data-types/02-string/4-extract-currency/solution.md diff --git a/1-js/4-data-types/09-string/4-extract-currency/task.md b/1-js/5-data-types/02-string/4-extract-currency/task.md similarity index 100% rename from 1-js/4-data-types/09-string/4-extract-currency/task.md rename to 1-js/5-data-types/02-string/4-extract-currency/task.md diff --git a/1-js/4-data-types/09-string/article.md b/1-js/5-data-types/02-string/article.md similarity index 91% rename from 1-js/4-data-types/09-string/article.md rename to 1-js/5-data-types/02-string/article.md index afdd2587..3d164405 100644 --- a/1-js/4-data-types/09-string/article.md +++ b/1-js/5-data-types/02-string/article.md @@ -1,4 +1,4 @@ -# Strings in-depth +# Strings In JavaScript, the textual data is stored as strings. There is no separate type for a single character. @@ -581,62 +581,26 @@ We actually have a single symbol in each of the strings above, but the `length` But, for instance, getting a symbol can be tricky, because surrogate pairs are treated as two characters: ```js run -alert( '𩷶'[0] ); // some strange symbols -alert( '𝒳'[0] ); // pieces of the surrogate pair +alert( '𝒳'[0] ); // strange symbols... +alert( '𝒳'[1] ); // ...pieces of the surrogate pair ``` Note that pieces of the surrogate pair have no meaning without each other. So, the alerts in the example above actually display garbage. -How to solve this problem? First, let's make sure you have it. Not every project deals with surrogate pairs. +Technically, surrogate pairs are also detectable by their codes: if a character has the code in the interval of `0xd800..0xdbff`, then it is the first part of the surrogate pair. The next character (second part) must have the code in interval `0xdc00..0xdfff`. These intervals are reserved exclusively for surrogate pairs by the standard. -If you do, then there are some more tricks to deal with surrogates: +In the case above: -Use `for..of` to iterate over characters. -: The `for..of` loop respects surrogate pairs: +```js run +// charCodeAt is not surrogate-pair aware, so it gives codes for parts - ```js run - let str = '𝒳😂'; - for(let char of str) { // loop over characters of str - alert(char); // 𝒳, and then 😂 - } - ``` +alert( '𝒳'.charCodeAt(0).toString(16) ); // d835, between 0xd800 and 0xdbff +alert( '𝒳'.charCodeAt(1).toString(16) ); // dcb3, between 0xdc00 and 0xdfff +``` -Create an array of characters using `Array.from(str)`: -: Here's the trick: +You will find more ways to deal with surrogate pairs later in the chapter . Probably, there are special libraries for that too, but nothing famous enough to suggest here. - ```js run - let str = '𝒳😂'; - - // splits str into array of characters - let chars = Array.from(str); - - alert(chars[0]); // 𝒳 - alert(chars[1]); // 😂 - alert(chars.length); // 2 - ``` - - The [Array.from](mdn:js/Array/from) takes an array-like object and turns it into a real array. It works with other array-like objects too. - - Technically here it does the same as: - - ```js run - let str = '𝒳😂'; - - let chars = []; // Array.from internally does the same loop - for(let char of str) { - chars.push(char); - } - - alert(chars); - ``` - - ...But is shorter. - -There are probably libraries in the internet that build surrogate-aware versions of other string calls based on that. - -Technically, surrogate pairs are also detectable by their codes: the first character has the code in the interval of `0xD800..0xDBFF`, while the second is in `0xDC00..0xDFFF`. So if we see a character with the code, say, `0xD801`, then the next one must be the second part of the surrogate pair. - -### Diacritical marks +### Diacritical marks and normalization In many languages there are symbols that are composed of the base character and a mark above/under it. @@ -660,7 +624,7 @@ The example: alert( 'S\u0307\u0323' ); // Ṩ ``` -This leads to great flexibility, but also an interesting problem: the same symbol visually can be represented with different unicode compositions. +This gives great flexibility, but also an interesting problem: the same symbol visually can be represented with different unicode compositions. For instance: @@ -679,7 +643,7 @@ It is implemented by [str.normalize()](mdn:js/String/normalize). alert( "S\u0307\u0323".normalize() == "S\u0323\u0307".normalize() ); // true ``` -It's rather funny that in that exactly situation `normalize()` brings a sequence of 3 characters to one: `\u1e68` (S with two dots). +It's funny that in our situation `normalize()` actually brings a sequence of 3 characters to one: `\u1e68` (S with two dots). ```js run alert( "S\u0307\u0323".normalize().length ); // 1 @@ -687,7 +651,7 @@ alert( "S\u0307\u0323".normalize().length ); // 1 alert( "S\u0307\u0323".normalize() == "\u1e68" ); // true ``` -In real, that is not always so. It's just the symbol `Ṩ` is "common enough" so that UTF-16 creators included it into the main table and gave it the code. +In real, that is not always so. The reason is that symbol `Ṩ` is "common enough", so UTF-16 creators included it into the main table and gave it the code. If you want to learn more about normalization rules and variants -- they are described in the appendix to the Unicode standard: [Unicode Normalization Forms](http://www.unicode.org/reports/tr15/), but for most practical reasons the information from this section is enough. @@ -698,7 +662,7 @@ If you want to learn more about normalization rules and variants -- they are des - Strings in JavaScript are encoded using UTF-16. - We can use special characters like `\n` and insert letters by their unicode using `\u...`. - To get a character: use `[]`. -- To get a substring: use `slice` or `substr/substring`. +- To get a substring: use `slice` or `substring`. - To lowercase/uppercase a string: use `toLowerCase/toUpperCase`. - To look for a substring: use `indexOf`, or `includes/startsWith/endsWith` for simple checks. - To compare strings according to the language, use `localeCompare`, otherwise they are compared by character codes. diff --git a/1-js/4-data-types/17-date/1-new-date/solution.md b/1-js/5-data-types/03-date/1-new-date/solution.md similarity index 100% rename from 1-js/4-data-types/17-date/1-new-date/solution.md rename to 1-js/5-data-types/03-date/1-new-date/solution.md diff --git a/1-js/4-data-types/17-date/1-new-date/task.md b/1-js/5-data-types/03-date/1-new-date/task.md similarity index 100% rename from 1-js/4-data-types/17-date/1-new-date/task.md rename to 1-js/5-data-types/03-date/1-new-date/task.md diff --git a/1-js/4-data-types/17-date/2-get-week-day/_js.view/solution.js b/1-js/5-data-types/03-date/2-get-week-day/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/17-date/2-get-week-day/_js.view/solution.js rename to 1-js/5-data-types/03-date/2-get-week-day/_js.view/solution.js diff --git a/1-js/4-data-types/17-date/2-get-week-day/_js.view/test.js b/1-js/5-data-types/03-date/2-get-week-day/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/17-date/2-get-week-day/_js.view/test.js rename to 1-js/5-data-types/03-date/2-get-week-day/_js.view/test.js diff --git a/1-js/4-data-types/17-date/2-get-week-day/solution.md b/1-js/5-data-types/03-date/2-get-week-day/solution.md similarity index 100% rename from 1-js/4-data-types/17-date/2-get-week-day/solution.md rename to 1-js/5-data-types/03-date/2-get-week-day/solution.md diff --git a/1-js/4-data-types/17-date/2-get-week-day/task.md b/1-js/5-data-types/03-date/2-get-week-day/task.md similarity index 100% rename from 1-js/4-data-types/17-date/2-get-week-day/task.md rename to 1-js/5-data-types/03-date/2-get-week-day/task.md diff --git a/1-js/4-data-types/17-date/3-weekday/_js.view/solution.js b/1-js/5-data-types/03-date/3-weekday/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/17-date/3-weekday/_js.view/solution.js rename to 1-js/5-data-types/03-date/3-weekday/_js.view/solution.js diff --git a/1-js/4-data-types/17-date/3-weekday/_js.view/test.js b/1-js/5-data-types/03-date/3-weekday/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/17-date/3-weekday/_js.view/test.js rename to 1-js/5-data-types/03-date/3-weekday/_js.view/test.js diff --git a/1-js/4-data-types/17-date/3-weekday/solution.md b/1-js/5-data-types/03-date/3-weekday/solution.md similarity index 100% rename from 1-js/4-data-types/17-date/3-weekday/solution.md rename to 1-js/5-data-types/03-date/3-weekday/solution.md diff --git a/1-js/4-data-types/17-date/3-weekday/task.md b/1-js/5-data-types/03-date/3-weekday/task.md similarity index 100% rename from 1-js/4-data-types/17-date/3-weekday/task.md rename to 1-js/5-data-types/03-date/3-weekday/task.md diff --git a/1-js/4-data-types/17-date/4-get-date-ago/_js.view/solution.js b/1-js/5-data-types/03-date/4-get-date-ago/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/17-date/4-get-date-ago/_js.view/solution.js rename to 1-js/5-data-types/03-date/4-get-date-ago/_js.view/solution.js diff --git a/1-js/4-data-types/17-date/4-get-date-ago/_js.view/test.js b/1-js/5-data-types/03-date/4-get-date-ago/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/17-date/4-get-date-ago/_js.view/test.js rename to 1-js/5-data-types/03-date/4-get-date-ago/_js.view/test.js diff --git a/1-js/4-data-types/17-date/4-get-date-ago/solution.md b/1-js/5-data-types/03-date/4-get-date-ago/solution.md similarity index 100% rename from 1-js/4-data-types/17-date/4-get-date-ago/solution.md rename to 1-js/5-data-types/03-date/4-get-date-ago/solution.md diff --git a/1-js/4-data-types/17-date/4-get-date-ago/task.md b/1-js/5-data-types/03-date/4-get-date-ago/task.md similarity index 100% rename from 1-js/4-data-types/17-date/4-get-date-ago/task.md rename to 1-js/5-data-types/03-date/4-get-date-ago/task.md diff --git a/1-js/4-data-types/17-date/5-last-day-of-month/_js.view/solution.js b/1-js/5-data-types/03-date/5-last-day-of-month/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/17-date/5-last-day-of-month/_js.view/solution.js rename to 1-js/5-data-types/03-date/5-last-day-of-month/_js.view/solution.js diff --git a/1-js/4-data-types/17-date/5-last-day-of-month/_js.view/test.js b/1-js/5-data-types/03-date/5-last-day-of-month/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/17-date/5-last-day-of-month/_js.view/test.js rename to 1-js/5-data-types/03-date/5-last-day-of-month/_js.view/test.js diff --git a/1-js/4-data-types/17-date/5-last-day-of-month/solution.md b/1-js/5-data-types/03-date/5-last-day-of-month/solution.md similarity index 100% rename from 1-js/4-data-types/17-date/5-last-day-of-month/solution.md rename to 1-js/5-data-types/03-date/5-last-day-of-month/solution.md diff --git a/1-js/4-data-types/17-date/5-last-day-of-month/task.md b/1-js/5-data-types/03-date/5-last-day-of-month/task.md similarity index 100% rename from 1-js/4-data-types/17-date/5-last-day-of-month/task.md rename to 1-js/5-data-types/03-date/5-last-day-of-month/task.md diff --git a/1-js/4-data-types/17-date/6-get-seconds-today/solution.md b/1-js/5-data-types/03-date/6-get-seconds-today/solution.md similarity index 100% rename from 1-js/4-data-types/17-date/6-get-seconds-today/solution.md rename to 1-js/5-data-types/03-date/6-get-seconds-today/solution.md diff --git a/1-js/4-data-types/17-date/6-get-seconds-today/task.md b/1-js/5-data-types/03-date/6-get-seconds-today/task.md similarity index 100% rename from 1-js/4-data-types/17-date/6-get-seconds-today/task.md rename to 1-js/5-data-types/03-date/6-get-seconds-today/task.md diff --git a/1-js/4-data-types/17-date/7-get-seconds-to-tomorrow/solution.md b/1-js/5-data-types/03-date/7-get-seconds-to-tomorrow/solution.md similarity index 100% rename from 1-js/4-data-types/17-date/7-get-seconds-to-tomorrow/solution.md rename to 1-js/5-data-types/03-date/7-get-seconds-to-tomorrow/solution.md diff --git a/1-js/4-data-types/17-date/7-get-seconds-to-tomorrow/task.md b/1-js/5-data-types/03-date/7-get-seconds-to-tomorrow/task.md similarity index 100% rename from 1-js/4-data-types/17-date/7-get-seconds-to-tomorrow/task.md rename to 1-js/5-data-types/03-date/7-get-seconds-to-tomorrow/task.md diff --git a/1-js/4-data-types/17-date/8-format-date-ddmmyy/_js.view/solution.js b/1-js/5-data-types/03-date/8-format-date-ddmmyy/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/17-date/8-format-date-ddmmyy/_js.view/solution.js rename to 1-js/5-data-types/03-date/8-format-date-ddmmyy/_js.view/solution.js diff --git a/1-js/4-data-types/17-date/8-format-date-ddmmyy/_js.view/test.js b/1-js/5-data-types/03-date/8-format-date-ddmmyy/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/17-date/8-format-date-ddmmyy/_js.view/test.js rename to 1-js/5-data-types/03-date/8-format-date-ddmmyy/_js.view/test.js diff --git a/1-js/4-data-types/17-date/8-format-date-ddmmyy/solution.md b/1-js/5-data-types/03-date/8-format-date-ddmmyy/solution.md similarity index 100% rename from 1-js/4-data-types/17-date/8-format-date-ddmmyy/solution.md rename to 1-js/5-data-types/03-date/8-format-date-ddmmyy/solution.md diff --git a/1-js/4-data-types/17-date/8-format-date-ddmmyy/task.md b/1-js/5-data-types/03-date/8-format-date-ddmmyy/task.md similarity index 100% rename from 1-js/4-data-types/17-date/8-format-date-ddmmyy/task.md rename to 1-js/5-data-types/03-date/8-format-date-ddmmyy/task.md diff --git a/1-js/4-data-types/17-date/9-format-date-relative/_js.view/solution.js b/1-js/5-data-types/03-date/9-format-date-relative/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/17-date/9-format-date-relative/_js.view/solution.js rename to 1-js/5-data-types/03-date/9-format-date-relative/_js.view/solution.js diff --git a/1-js/4-data-types/17-date/9-format-date-relative/_js.view/test.js b/1-js/5-data-types/03-date/9-format-date-relative/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/17-date/9-format-date-relative/_js.view/test.js rename to 1-js/5-data-types/03-date/9-format-date-relative/_js.view/test.js diff --git a/1-js/4-data-types/17-date/9-format-date-relative/solution.md b/1-js/5-data-types/03-date/9-format-date-relative/solution.md similarity index 100% rename from 1-js/4-data-types/17-date/9-format-date-relative/solution.md rename to 1-js/5-data-types/03-date/9-format-date-relative/solution.md diff --git a/1-js/4-data-types/17-date/9-format-date-relative/task.md b/1-js/5-data-types/03-date/9-format-date-relative/task.md similarity index 100% rename from 1-js/4-data-types/17-date/9-format-date-relative/task.md rename to 1-js/5-data-types/03-date/9-format-date-relative/task.md diff --git a/1-js/4-data-types/17-date/article.md b/1-js/5-data-types/03-date/article.md similarity index 65% rename from 1-js/4-data-types/17-date/article.md rename to 1-js/5-data-types/03-date/article.md index 50a992f0..29f560f2 100644 --- a/1-js/4-data-types/17-date/article.md +++ b/1-js/5-data-types/03-date/article.md @@ -1,4 +1,4 @@ -# Date and time [todo: performance.now for future] +# Date and time JavaScript has a built-in object [Date](mdn:js/Date) for date/time management. @@ -200,7 +200,7 @@ alert( date ); // 31 Dec 2015 ## Date to number, date diff -A `Date` object can be converted to a number, it becomes the number of milliseconds: +When a `Date` object is converted to number, it becomes its number of milliseconds: ```js run let date = new Date(); @@ -224,151 +224,144 @@ let end = new Date(); // done alert( `The loop took ${end - start} ms` ); ``` -## Benchmarking, performance.now +## Date.now() -If we want a reliable benchmark of CPU-hungry function, we should be more careful. +If we only want to measure the difference, we don't need `Date` object. -For instance, let's consider two functions to walk the array: +There's a special method `Date.now()` that returns the current timestamp. -```js -function walkIn(arr) { - for (let key in arr) arr[key]++; +It is semantically equivalent to `new Date().getTime()`, but it does not create an intermediate `Date` object. So it's faster and does not put pressure on garbage collection. + +It is used mostly for convenience or when performance matters, like in games in JavaScript or other specialized applications. + +So this is probably better: + +```js run +*!* +let start = Date.now(); // milliseconds count from 1 Jan 1970 +*/!* + +// do the job +for (let i = 0; i < 100000; i++) { + let doSomething = i * i * i; } -function walkLength(arr) { - for (let i = 0; i < arr.length; i++) arr[i]++; +*!* +let end = Date.now(); // done +*/!* + +alert( `The loop took ${end - start} ms` ); // substract numbers, not dates +``` + +## Benchmarking + +If we want a reliable benchmark of CPU-hungry function, we should be careful. + +For instance, let's measure two function that get a delta between two dates, which one is faster? + +```js +function diffSubstract(date1, date2) { + return date2 - date1; +} + +function diffGetTime(date1, date2) { + return date2.getTime() - date1.getTime(); } ``` -We can't run each of them once, and check the time difference. A single run is unreliable, a tiny CPU spike will spoil the result. +These two do exactly the same, because when dates are substracted, they are coerced into numbers of milliseconds, exactly the same thing as `date.getTime()` returns. -For the right benchmarking, we need to run each function many times, for the test to take considerable time. Then sudden CPU spikes will not affect it a lot. +The first idea is to run them many times in a row and measure the difference. For our case, functions are very simple, so we have to do it around 100000 times. -A complex function may be run a few times, but here the functions are simple, so we need to run them 1000 times. - -Let's measure which one is faster: +Let's measure: ```js run -let arr = []; -for (let i = 0; i < 1000; i++) arr[i] = 0; - -function walkIn(arr) { - for (let key in arr) arr[key]++; +function diffSubstract(date1, date2) { + return date2 - date1; } -function walkLength(arr) { - for (let i = 0; i < arr.length; i++) arr[i]++; +function diffGetTime(date1, date2) { + return date2.getTime() - date1.getTime(); } function bench(f) { - let date = new Date(); - for (let i = 0; i < 10000; i++) f(arr); - return new Date() - date; + let date1 = new Date(0); + let date2 = new Date(); + + let start = Date.now(); + for (let i = 0; i < 100000; i++) f(date1, date2); + return Date.now() - start; } -alert( 'Time of walkIn: ' + bench(walkIn) + 'ms' ); -alert( 'Time walkLength: ' + bench(walkLength) + 'ms' ); +alert( 'Time of diffSubstract: ' + bench(diffSubstract) + 'ms' ); +alert( 'Time of diffGetTime: ' + bench(diffGetTime) + 'ms' ); ``` -Now let's improve that a little bit more. Imagine that in the time of the first benchmarking `bench(walkIn)` the CPU was doing something in parallel, and it was taking resources. And at the time of the second benchmark the work was finished. +Wow! Using `getTime()` is so much faster! That's because there's no type conversion, it is much easier for engines to optimize. + +Okay, we have something. But that's not a good benchmark yet. + +Imagine that in the time of running `bench(diffSubstract)` CPU was doing something in parallel, and it was taking resources. And at the time of the second benchmark the work was finished. Is that real? Of course it is, especially for the modern multi-process OS. -As a result, the first benchmark will have less CPU resources than the second. Again, a reason for wrong results. +As a result, the first benchmark will have less CPU resources than the second. That's a reason for wrong results. -**For the more reliable benchmarking, the whole pack of benchmarks should be rerun multiple times.** +**For more reliable benchmarking, the whole pack of benchmarks should be rerun multiple times.** Here's the code example: ```js run -let arr = []; -for (let i = 0; i < 1000; i++) arr[i] = 0; - -function walkIn(arr) { - for (let key in arr) arr[key]++; +function diffSubstract(date1, date2) { + return date2 - date1; } -function walkLength(arr) { - for (let i = 0; i < arr.length; i++) arr[i]++; +function diffGetTime(date1, date2) { + return date2.getTime() - date1.getTime(); } function bench(f) { - let date = new Date(); - for (let i = 0; i < 1000; i++) f(arr); - return new Date() - date; + let date1 = new Date(0); + let date2 = new Date(); + + let start = Date.now(); + for (let i = 0; i < 100000; i++) f(date1, date2); + return Date.now() - start; } -let timeWalkIn = 0; -let timeWalkLength = 0; +let time1 = 0; +let time2 = 0; *!* -// run bench(walkIn) and bench(walkLength) each 100 times alternating -for (let i = 0; i < 100; i++) { - timeWalkIn += bench(walkIn); - timeWalkLength += bench(walkLength); +// run bench(upperSlice) and bench(upperLoop) each 10 times alternating +for (let i = 0; i < 10; i++) { + time1 += bench(diffSubstract); + time2 += bench(diffGetTime); } */!* -alert( 'Total time for walkIn: ' + timeWalkIn ); -alert( 'Total time for walkLength: ' + timeWalkLength ); +alert( 'Total time for diffSubstract: ' + time1 ); +alert( 'Total time for diffGetTime: ' + time2 ); ``` -That's also important because modern JavaScript engines start applying advanced optimizations only to the "hot code" that executes many times (no need to optimize rarely executed things). So, in the example above, first executions are not well-optimized. We may want to throw away the results of the first run. +Modern JavaScript engines start applying advanced optimizations only to "hot code" that executes many times (no need to optimize rarely executed things). So, in the example above, first executions are not well-optimized. We may want to add a heat-up run: -````smart header="`console.time(метка)` и `console.timeEnd(метка)`" -Modern browsers support the following methods for benchmarking with the immediate output: +```js +// heat up +bench(diffSubstract); +bench(diffGetTime); -- `console.time(label)` -- start the built-in chronometer with the given label. -- `console.timeEnd(label)` -- start the built-in chronometer with the given label and output the result. - -The `label` parameter allows to start parallel measurements. - -In the code below, there are timers `walkIn`, `walkLength` -- for the individual benchmarks and "All Benchmarks" -- for the whole time: - -```js run -let arr = []; -for (let i = 0; i < 1000; i++) arr[i] = 0; - -function walkIn(arr) { - for (let key in arr) arr[key]++; +// now benchmark +for (let i = 0; i < 10; i++) { + time1 += bench(diffSubstract); + time2 += bench(diffGetTime); } - -function walkLength(arr) { - for (let i = 0; i < arr.length; i++) arr[i]++; -} - -function bench(f) { - for (let i = 0; i < 10000; i++) f(arr); -} - -console.time("All Benchmarks"); - -console.time("walkIn"); -bench(walkIn); -console.timeEnd("walkIn"); - -console.time("walkLength"); -bench(walkLength); -console.timeEnd("walkLength"); - -console.timeEnd("All Benchmarks"); ``` -If you are running the example, please open the developer console, otherwise you won't see the output. -```` - ```warn header="Be careful doing micro-benchmarking" -Modern JavaScript engines perform many optimizations, like: +Modern JavaScript engines perform many optimizations. Some of them may tweak artificial tests results compared to normal usage. -1. Move loop invariants -- unchanging values like `arr.length` out of the loop. -2. Try to understand which type of values is stored in the variable and optimize its storage. -3. Try to understand the structure of an object, and if we have many objects with the same structure, optimize the case. -4. Do simple constant folding, calculating expressions like `2 + 3` or `"str1" + "str2"` before the code is executed. -5. See if a variable is not used and remove it. - -...And many other stuff. Of course that affects benchmark results, especially when we measure "micro" things like walking an array. - -So if you seriously want to understand performance, then please first study how the JavaScript engine works. And then you probably won't need microbenchmarks at all, or apply them very rarely. +So if you seriously want to understand performance, then please first study how the JavaScript engine works. And then you probably won't need microbenchmarks at all, or apply them rarely. The great pack of articles about V8 can be found at . ``` @@ -404,13 +397,6 @@ let date = new Date( Date.parse('2012-01-26T13:51:50.417-07:00') ); alert( date ); ``` -## Date.now() - -The call to `Date.now()` returns the current timestamp, or, in other words, the number of milliseconds that passed since 01 Jan 1970 till now. - -It is semantically equivalent to `new Date().getTime()`, but it does not create an intermediate `Date` object. - -It is used mostly for convenience or when the performance is critical, like games in JavaScript or other specialized applications. ## Summary @@ -423,3 +409,21 @@ It is used mostly for convenience or when the performance is critical, like game Note that unlike many other systems, timestamps in JavaScript are in milliseconds, not in seconds. +Also, sometimes we need more precise time measurements. Javascript itself does not have a way to measure time in microseconds (1 millionth of a second), but most environments provide it. + +For instance, browser has [performance.now()](mdn:api/Performance/now) that gives the number of milliseconds from the start of page loading, but adds 3 digits after the point to it. So totally it becomes microsecond percision: + +```js run +alert(`Loading started ${performance.now()}ms ago`); +// Something like: "Loading started 34731.26000000001ms ago" +// it may show more than 3 digits after the decimal point, but only 3 first are correct +``` + +Node.JS has `microtime` module and other ways. Technically, any device and environment allows to get that, it's just not in `Date`. + + + + + + + diff --git a/1-js/4-data-types/11-array/1-item-value/solution.md b/1-js/5-data-types/04-array/1-item-value/solution.md similarity index 100% rename from 1-js/4-data-types/11-array/1-item-value/solution.md rename to 1-js/5-data-types/04-array/1-item-value/solution.md diff --git a/1-js/4-data-types/11-array/1-item-value/task.md b/1-js/5-data-types/04-array/1-item-value/task.md similarity index 100% rename from 1-js/4-data-types/11-array/1-item-value/task.md rename to 1-js/5-data-types/04-array/1-item-value/task.md diff --git a/1-js/4-data-types/11-array/10-maximal-subarray/_js.view/solution.js b/1-js/5-data-types/04-array/10-maximal-subarray/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/11-array/10-maximal-subarray/_js.view/solution.js rename to 1-js/5-data-types/04-array/10-maximal-subarray/_js.view/solution.js diff --git a/1-js/4-data-types/11-array/10-maximal-subarray/_js.view/test.js b/1-js/5-data-types/04-array/10-maximal-subarray/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/11-array/10-maximal-subarray/_js.view/test.js rename to 1-js/5-data-types/04-array/10-maximal-subarray/_js.view/test.js diff --git a/1-js/4-data-types/11-array/10-maximal-subarray/solution.md b/1-js/5-data-types/04-array/10-maximal-subarray/solution.md similarity index 100% rename from 1-js/4-data-types/11-array/10-maximal-subarray/solution.md rename to 1-js/5-data-types/04-array/10-maximal-subarray/solution.md diff --git a/1-js/4-data-types/11-array/10-maximal-subarray/task.md b/1-js/5-data-types/04-array/10-maximal-subarray/task.md similarity index 100% rename from 1-js/4-data-types/11-array/10-maximal-subarray/task.md rename to 1-js/5-data-types/04-array/10-maximal-subarray/task.md diff --git a/1-js/4-data-types/11-array/2-create-array/solution.md b/1-js/5-data-types/04-array/2-create-array/solution.md similarity index 100% rename from 1-js/4-data-types/11-array/2-create-array/solution.md rename to 1-js/5-data-types/04-array/2-create-array/solution.md diff --git a/1-js/4-data-types/11-array/2-create-array/task.md b/1-js/5-data-types/04-array/2-create-array/task.md similarity index 100% rename from 1-js/4-data-types/11-array/2-create-array/task.md rename to 1-js/5-data-types/04-array/2-create-array/task.md diff --git a/1-js/4-data-types/11-array/3-call-array-this/solution.md b/1-js/5-data-types/04-array/3-call-array-this/solution.md similarity index 100% rename from 1-js/4-data-types/11-array/3-call-array-this/solution.md rename to 1-js/5-data-types/04-array/3-call-array-this/solution.md diff --git a/1-js/4-data-types/11-array/3-call-array-this/task.md b/1-js/5-data-types/04-array/3-call-array-this/task.md similarity index 100% rename from 1-js/4-data-types/11-array/3-call-array-this/task.md rename to 1-js/5-data-types/04-array/3-call-array-this/task.md diff --git a/1-js/4-data-types/11-array/5-array-input-sum/solution.md b/1-js/5-data-types/04-array/5-array-input-sum/solution.md similarity index 100% rename from 1-js/4-data-types/11-array/5-array-input-sum/solution.md rename to 1-js/5-data-types/04-array/5-array-input-sum/solution.md diff --git a/1-js/4-data-types/11-array/5-array-input-sum/task.md b/1-js/5-data-types/04-array/5-array-input-sum/task.md similarity index 100% rename from 1-js/4-data-types/11-array/5-array-input-sum/task.md rename to 1-js/5-data-types/04-array/5-array-input-sum/task.md diff --git a/1-js/4-data-types/11-array/array-pop.png b/1-js/5-data-types/04-array/array-pop.png similarity index 100% rename from 1-js/4-data-types/11-array/array-pop.png rename to 1-js/5-data-types/04-array/array-pop.png diff --git a/1-js/4-data-types/11-array/array-pop@2x.png b/1-js/5-data-types/04-array/array-pop@2x.png similarity index 100% rename from 1-js/4-data-types/11-array/array-pop@2x.png rename to 1-js/5-data-types/04-array/array-pop@2x.png diff --git a/1-js/4-data-types/11-array/array-shift.png b/1-js/5-data-types/04-array/array-shift.png similarity index 100% rename from 1-js/4-data-types/11-array/array-shift.png rename to 1-js/5-data-types/04-array/array-shift.png diff --git a/1-js/4-data-types/11-array/array-shift@2x.png b/1-js/5-data-types/04-array/array-shift@2x.png similarity index 100% rename from 1-js/4-data-types/11-array/array-shift@2x.png rename to 1-js/5-data-types/04-array/array-shift@2x.png diff --git a/1-js/4-data-types/11-array/array-speed.png b/1-js/5-data-types/04-array/array-speed.png similarity index 100% rename from 1-js/4-data-types/11-array/array-speed.png rename to 1-js/5-data-types/04-array/array-speed.png diff --git a/1-js/4-data-types/11-array/array-speed@2x.png b/1-js/5-data-types/04-array/array-speed@2x.png similarity index 100% rename from 1-js/4-data-types/11-array/array-speed@2x.png rename to 1-js/5-data-types/04-array/array-speed@2x.png diff --git a/1-js/4-data-types/11-array/article.md b/1-js/5-data-types/04-array/article.md similarity index 100% rename from 1-js/4-data-types/11-array/article.md rename to 1-js/5-data-types/04-array/article.md diff --git a/1-js/4-data-types/11-array/queue.png b/1-js/5-data-types/04-array/queue.png similarity index 100% rename from 1-js/4-data-types/11-array/queue.png rename to 1-js/5-data-types/04-array/queue.png diff --git a/1-js/4-data-types/11-array/queue@2x.png b/1-js/5-data-types/04-array/queue@2x.png similarity index 100% rename from 1-js/4-data-types/11-array/queue@2x.png rename to 1-js/5-data-types/04-array/queue@2x.png diff --git a/1-js/4-data-types/11-array/stack.png b/1-js/5-data-types/04-array/stack.png similarity index 100% rename from 1-js/4-data-types/11-array/stack.png rename to 1-js/5-data-types/04-array/stack.png diff --git a/1-js/4-data-types/11-array/stack@2x.png b/1-js/5-data-types/04-array/stack@2x.png similarity index 100% rename from 1-js/4-data-types/11-array/stack@2x.png rename to 1-js/5-data-types/04-array/stack@2x.png diff --git a/1-js/4-data-types/12-array-methods/1-camelcase/_js.view/solution.js b/1-js/5-data-types/05-array-methods/1-camelcase/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/12-array-methods/1-camelcase/_js.view/solution.js rename to 1-js/5-data-types/05-array-methods/1-camelcase/_js.view/solution.js diff --git a/1-js/4-data-types/12-array-methods/1-camelcase/_js.view/test.js b/1-js/5-data-types/05-array-methods/1-camelcase/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/12-array-methods/1-camelcase/_js.view/test.js rename to 1-js/5-data-types/05-array-methods/1-camelcase/_js.view/test.js diff --git a/1-js/4-data-types/12-array-methods/1-camelcase/solution.md b/1-js/5-data-types/05-array-methods/1-camelcase/solution.md similarity index 100% rename from 1-js/4-data-types/12-array-methods/1-camelcase/solution.md rename to 1-js/5-data-types/05-array-methods/1-camelcase/solution.md diff --git a/1-js/4-data-types/12-array-methods/1-camelcase/task.md b/1-js/5-data-types/05-array-methods/1-camelcase/task.md similarity index 100% rename from 1-js/4-data-types/12-array-methods/1-camelcase/task.md rename to 1-js/5-data-types/05-array-methods/1-camelcase/task.md diff --git a/1-js/4-data-types/12-array-methods/11-array-unique/_js.view/solution.js b/1-js/5-data-types/05-array-methods/11-array-unique/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/12-array-methods/11-array-unique/_js.view/solution.js rename to 1-js/5-data-types/05-array-methods/11-array-unique/_js.view/solution.js diff --git a/1-js/4-data-types/12-array-methods/11-array-unique/_js.view/test.js b/1-js/5-data-types/05-array-methods/11-array-unique/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/12-array-methods/11-array-unique/_js.view/test.js rename to 1-js/5-data-types/05-array-methods/11-array-unique/_js.view/test.js diff --git a/1-js/4-data-types/12-array-methods/11-array-unique/solution.md b/1-js/5-data-types/05-array-methods/11-array-unique/solution.md similarity index 100% rename from 1-js/4-data-types/12-array-methods/11-array-unique/solution.md rename to 1-js/5-data-types/05-array-methods/11-array-unique/solution.md diff --git a/1-js/4-data-types/12-array-methods/11-array-unique/task.md b/1-js/5-data-types/05-array-methods/11-array-unique/task.md similarity index 100% rename from 1-js/4-data-types/12-array-methods/11-array-unique/task.md rename to 1-js/5-data-types/05-array-methods/11-array-unique/task.md diff --git a/1-js/4-data-types/12-array-methods/2-filter-range/_js.view/solution.js b/1-js/5-data-types/05-array-methods/2-filter-range/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/12-array-methods/2-filter-range/_js.view/solution.js rename to 1-js/5-data-types/05-array-methods/2-filter-range/_js.view/solution.js diff --git a/1-js/4-data-types/12-array-methods/2-filter-range/_js.view/test.js b/1-js/5-data-types/05-array-methods/2-filter-range/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/12-array-methods/2-filter-range/_js.view/test.js rename to 1-js/5-data-types/05-array-methods/2-filter-range/_js.view/test.js diff --git a/1-js/4-data-types/12-array-methods/2-filter-range/solution.md b/1-js/5-data-types/05-array-methods/2-filter-range/solution.md similarity index 100% rename from 1-js/4-data-types/12-array-methods/2-filter-range/solution.md rename to 1-js/5-data-types/05-array-methods/2-filter-range/solution.md diff --git a/1-js/4-data-types/12-array-methods/2-filter-range/task.md b/1-js/5-data-types/05-array-methods/2-filter-range/task.md similarity index 100% rename from 1-js/4-data-types/12-array-methods/2-filter-range/task.md rename to 1-js/5-data-types/05-array-methods/2-filter-range/task.md diff --git a/1-js/4-data-types/12-array-methods/3-filter-range-in-place/_js.view/solution.js b/1-js/5-data-types/05-array-methods/3-filter-range-in-place/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/12-array-methods/3-filter-range-in-place/_js.view/solution.js rename to 1-js/5-data-types/05-array-methods/3-filter-range-in-place/_js.view/solution.js diff --git a/1-js/4-data-types/12-array-methods/3-filter-range-in-place/_js.view/test.js b/1-js/5-data-types/05-array-methods/3-filter-range-in-place/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/12-array-methods/3-filter-range-in-place/_js.view/test.js rename to 1-js/5-data-types/05-array-methods/3-filter-range-in-place/_js.view/test.js diff --git a/1-js/4-data-types/12-array-methods/3-filter-range-in-place/solution.md b/1-js/5-data-types/05-array-methods/3-filter-range-in-place/solution.md similarity index 100% rename from 1-js/4-data-types/12-array-methods/3-filter-range-in-place/solution.md rename to 1-js/5-data-types/05-array-methods/3-filter-range-in-place/solution.md diff --git a/1-js/4-data-types/12-array-methods/3-filter-range-in-place/task.md b/1-js/5-data-types/05-array-methods/3-filter-range-in-place/task.md similarity index 100% rename from 1-js/4-data-types/12-array-methods/3-filter-range-in-place/task.md rename to 1-js/5-data-types/05-array-methods/3-filter-range-in-place/task.md diff --git a/1-js/4-data-types/12-array-methods/4-sort-back/solution.md b/1-js/5-data-types/05-array-methods/4-sort-back/solution.md similarity index 100% rename from 1-js/4-data-types/12-array-methods/4-sort-back/solution.md rename to 1-js/5-data-types/05-array-methods/4-sort-back/solution.md diff --git a/1-js/4-data-types/12-array-methods/4-sort-back/task.md b/1-js/5-data-types/05-array-methods/4-sort-back/task.md similarity index 100% rename from 1-js/4-data-types/12-array-methods/4-sort-back/task.md rename to 1-js/5-data-types/05-array-methods/4-sort-back/task.md diff --git a/1-js/4-data-types/12-array-methods/5-copy-sort-array/solution.md b/1-js/5-data-types/05-array-methods/5-copy-sort-array/solution.md similarity index 100% rename from 1-js/4-data-types/12-array-methods/5-copy-sort-array/solution.md rename to 1-js/5-data-types/05-array-methods/5-copy-sort-array/solution.md diff --git a/1-js/4-data-types/12-array-methods/5-copy-sort-array/task.md b/1-js/5-data-types/05-array-methods/5-copy-sort-array/task.md similarity index 100% rename from 1-js/4-data-types/12-array-methods/5-copy-sort-array/task.md rename to 1-js/5-data-types/05-array-methods/5-copy-sort-array/task.md diff --git a/1-js/4-data-types/12-array-methods/6-array-get-names/solution.md b/1-js/5-data-types/05-array-methods/6-array-get-names/solution.md similarity index 100% rename from 1-js/4-data-types/12-array-methods/6-array-get-names/solution.md rename to 1-js/5-data-types/05-array-methods/6-array-get-names/solution.md diff --git a/1-js/4-data-types/12-array-methods/6-array-get-names/task.md b/1-js/5-data-types/05-array-methods/6-array-get-names/task.md similarity index 100% rename from 1-js/4-data-types/12-array-methods/6-array-get-names/task.md rename to 1-js/5-data-types/05-array-methods/6-array-get-names/task.md diff --git a/1-js/4-data-types/12-array-methods/7-sort-objects/solution.md b/1-js/5-data-types/05-array-methods/7-sort-objects/solution.md similarity index 100% rename from 1-js/4-data-types/12-array-methods/7-sort-objects/solution.md rename to 1-js/5-data-types/05-array-methods/7-sort-objects/solution.md diff --git a/1-js/4-data-types/12-array-methods/7-sort-objects/task.md b/1-js/5-data-types/05-array-methods/7-sort-objects/task.md similarity index 100% rename from 1-js/4-data-types/12-array-methods/7-sort-objects/task.md rename to 1-js/5-data-types/05-array-methods/7-sort-objects/task.md diff --git a/1-js/4-data-types/12-array-methods/8-average-age/solution.md b/1-js/5-data-types/05-array-methods/8-average-age/solution.md similarity index 100% rename from 1-js/4-data-types/12-array-methods/8-average-age/solution.md rename to 1-js/5-data-types/05-array-methods/8-average-age/solution.md diff --git a/1-js/4-data-types/12-array-methods/8-average-age/task.md b/1-js/5-data-types/05-array-methods/8-average-age/task.md similarity index 100% rename from 1-js/4-data-types/12-array-methods/8-average-age/task.md rename to 1-js/5-data-types/05-array-methods/8-average-age/task.md diff --git a/1-js/4-data-types/12-array-methods/article.md b/1-js/5-data-types/05-array-methods/article.md similarity index 98% rename from 1-js/4-data-types/12-array-methods/article.md rename to 1-js/5-data-types/05-array-methods/article.md index ff1265ef..7f1fa371 100644 --- a/1-js/4-data-types/12-array-methods/article.md +++ b/1-js/5-data-types/05-array-methods/article.md @@ -172,7 +172,7 @@ alert( arr.concat([3, 4], [5, 6])); // 1,2,3,4,5,6 alert( arr.concat([3, 4], 5, 6)); // 1,2,3,4,5,6 ``` -Normally, it only copies elements from arrays ("spreads" them), array-likes or iterables are treated as regular values and added as a whole: +Normally, it only copies elements from arrays ("spreads" them), other objects even if they look like arrays and added as a whole: ```js run let arr = [1, 2]; @@ -186,7 +186,7 @@ alert( arr.concat(arrayLike) ); // 1,2,[object Object] //[1, 2, arrayLike] ``` -...But if an array-like has `Symbol.isConcatSpreadable` property, then its elements are added instead: +...But if an array-like object has `Symbol.isConcatSpreadable` property, then its elements are added instead: ```js run let arr = [1, 2]; @@ -668,10 +668,6 @@ We covered the most useful methods. But there are few others: - [arr.copyWithin(target, start, end)](mdn:js/Array/copyWithin) -- copies its elements from position `start` till position `end` into *itself*, at position `target` (overwrites existing). -- [arr.keys()](mdn:js/Array/keys) -- returns iterable over array indexes. - -- [arr.entries()](mdn:js/Array/entries) -- return iterables over array index/value pairs. - These and other methods are also listed in the [manual](mdn:js/Array). diff --git a/1-js/4-data-types/12-array-methods/reduce.png b/1-js/5-data-types/05-array-methods/reduce.png similarity index 100% rename from 1-js/4-data-types/12-array-methods/reduce.png rename to 1-js/5-data-types/05-array-methods/reduce.png diff --git a/1-js/4-data-types/12-array-methods/reduce@2x.png b/1-js/5-data-types/05-array-methods/reduce@2x.png similarity index 100% rename from 1-js/4-data-types/12-array-methods/reduce@2x.png rename to 1-js/5-data-types/05-array-methods/reduce@2x.png diff --git a/1-js/4-data-types/14-iterable/article.md b/1-js/5-data-types/06-iterable/article.md similarity index 77% rename from 1-js/4-data-types/14-iterable/article.md rename to 1-js/5-data-types/06-iterable/article.md index de81656d..de259815 100644 --- a/1-js/4-data-types/14-iterable/article.md +++ b/1-js/5-data-types/06-iterable/article.md @@ -32,7 +32,7 @@ To make the `range` iterable (and thus let `for..of` work) we need to add a meth - When `for..of` starts, it calls that method (or errors if none found). - The method must return an *iterator* -- an object with the method `next`. - When `for..of` wants the next value, it calls `next()` on that object. -- The result of `next()` must have the form `{done: Boolean, value: any}`: `done:true` means that the iteration is finished, otherwise `value` must be the new value. +- The result of `next()` must have the form `{done: Boolean, value: any}`, where `done=true` means that the iteration is finished, otherwise `value` must be the new value. Here's the full impelementation for `range`: @@ -40,7 +40,7 @@ Here's the full impelementation for `range`: let range = { from: 1, to: 5 -} +}; // 1. call to for..of initially calls this range[Symbol.iterator] = function() { @@ -99,7 +99,7 @@ let range = { ``` ```` -## Built-in iterables +## String is iterable Arrays and strings are most widely used built-in iterables. @@ -107,10 +107,20 @@ For a string, `for..of` loops over its characters: ```js run for(let char of "test") { - alert( char ); t, then e, then s, then t + alert( char ); // t, then e, then s, then t } ``` +And it works right with surrogate pairs! + +```js run +let str = '𝒳😂'; +for(let char of str) { + alert(char); // 𝒳, and then 😂 +} +``` + +````smart header="Calling an iterator manually" Iterators can also be created explicitly, without `for..of`, with a direct call of `Symbol.iterator`. For built-in objects too. For instance, this code gets a string iterator and calls it "manually": @@ -130,11 +140,12 @@ while(true) { } ``` -The same works for an array. +That is a little bit more flexible than `for..of`, because we can split the iteration process: iterate a bit, then stop, do something else, and then continue later. +```` -## Iterables VS array-likes [#array-like] +## Iterables and array-likes [#array-like] -There are two official terms that are similar, but actually very different. Please take care to avoid the confusion. +There are two official terms that are similar, but actually very different. Please be careful to avoid the confusion. - Iterables are objects that implement the `Symbol.iterator` method, as described above. - Array-likes are objects that have indexes and `length`, so they look like arrays. @@ -155,14 +166,16 @@ let arrayLike = { // has indexes and length => array-like }; *!* -// Error (not Symbol.iterator) +// Error (no Symbol.iterator) for(let item of arrayLike) {} */!* ``` But what they share in common -- both iterables and array-likes are usually *not arrays*, they don't have `push`, `pop` etc. That's rather inconvenient if we received such object and want to work with it as with an array. -There's a universal method [Array.from](mdn:js/Array/from) that brings them together. It takes an iterable *or* an array-like value and makes a "real" `Array` from it. Then we can call array methods on it. +## Array.from + +There's a universal method [Array.from](mdn:js/Array/from) that brings them together. It takes an iterable or array-like value and makes a "real" `Array` from it. Then we can call array methods on it. For instance: @@ -180,7 +193,7 @@ alert(arr.pop()); // World (method works) ```js // assuming that range is taken from the example above let arr = Array.from(range); -alert(arr); // 1,2,3,4,5 +alert(arr); // 1,2,3,4,5 (array toString conversion works) ``` The full syntax for `Array.from` allows to provide an optional "mapping" function: @@ -201,6 +214,51 @@ let arr = Array.from(range, num => num * num); alert(arr); // 1,4,9,16,25 ``` +We can also use `Array.from` to turn a string into array of characters: + +```js run +let str = '𝒳😂'; + +// splits str into array of characters +let chars = Array.from(str); + +alert(chars[0]); // 𝒳 +alert(chars[1]); // 😂 +alert(chars.length); // 2 +``` + +Unlike `str.split`, it relies on iterable nature of the string and so, just like `for..of`, correctly works with surrogate pairs. + +Technically here it does the same as: + +```js run +let str = '𝒳😂'; + +let chars = []; // Array.from internally does the same loop +for(let char of str) { + chars.push(char); +} + +alert(chars); +``` + +...But is shorter. + +We can even built surrogate-aware `slice` on it: + +```js run +function slice(str, start, end) { + return Array.from(str).slice(start, end).join(''); +} + +let str = '𝒳😂𩷶'; + +alert( slice(str, 1, 3) ); // 😂𩷶 + +// native method does not support surrogate pairs +alert( str.slice(1, 3) ); // garbage (two pieces from different surrogate pairs) +``` + ## Summary @@ -211,11 +269,13 @@ Objects that can be used in `for..of` are called *iterable*. - An iterator must have the method named `next()` that returns an object `{done: Boolean, value: any}`, here `done:true` denotes the iteration end, otherwise the `value` is the next value. - The `Symbol.iterator` method is called automatically by `for..of`, but we also can do it directly. - Built-in iterables like strings or arrays, also implement `Symbol.iterator`. +- String iterator knows about surrogate pairs. -The modern specification mostly uses iterables instead of arrays where an ordered collection is required, because they are more abstract. We'll see more examples of it very soon. Objects that have indexed properties and `length` are called *array-like*. Such objects may also have other properties and methods, but lack built-in methods of arrays. +If we look inside the specification -- we'll see that most built-in methods assume that they work with iterables or array-likes instead of "real" arrays, because that's more abstract. + `Array.from(obj[, mapFn, thisArg])` makes a real `Array` of an iterable or array-like `obj`, and then we can use array methods on it. The optional arguments `mapFn` and `thisArg` allow to apply a function to each item. diff --git a/1-js/4-data-types/15-map-set-weakmap-weakset/1-filter-anagrams/_js.view/solution.js b/1-js/5-data-types/07-map-set-weakmap-weakset/1-filter-anagrams/_js.view/solution.js similarity index 100% rename from 1-js/4-data-types/15-map-set-weakmap-weakset/1-filter-anagrams/_js.view/solution.js rename to 1-js/5-data-types/07-map-set-weakmap-weakset/1-filter-anagrams/_js.view/solution.js diff --git a/1-js/4-data-types/15-map-set-weakmap-weakset/1-filter-anagrams/_js.view/test.js b/1-js/5-data-types/07-map-set-weakmap-weakset/1-filter-anagrams/_js.view/test.js similarity index 100% rename from 1-js/4-data-types/15-map-set-weakmap-weakset/1-filter-anagrams/_js.view/test.js rename to 1-js/5-data-types/07-map-set-weakmap-weakset/1-filter-anagrams/_js.view/test.js diff --git a/1-js/4-data-types/15-map-set-weakmap-weakset/1-filter-anagrams/solution.md b/1-js/5-data-types/07-map-set-weakmap-weakset/1-filter-anagrams/solution.md similarity index 100% rename from 1-js/4-data-types/15-map-set-weakmap-weakset/1-filter-anagrams/solution.md rename to 1-js/5-data-types/07-map-set-weakmap-weakset/1-filter-anagrams/solution.md diff --git a/1-js/4-data-types/15-map-set-weakmap-weakset/1-filter-anagrams/task.md b/1-js/5-data-types/07-map-set-weakmap-weakset/1-filter-anagrams/task.md similarity index 100% rename from 1-js/4-data-types/15-map-set-weakmap-weakset/1-filter-anagrams/task.md rename to 1-js/5-data-types/07-map-set-weakmap-weakset/1-filter-anagrams/task.md diff --git a/1-js/4-data-types/15-map-set-weakmap-weakset/2-recipients-set/solution.md b/1-js/5-data-types/07-map-set-weakmap-weakset/2-recipients-set/solution.md similarity index 100% rename from 1-js/4-data-types/15-map-set-weakmap-weakset/2-recipients-set/solution.md rename to 1-js/5-data-types/07-map-set-weakmap-weakset/2-recipients-set/solution.md diff --git a/1-js/4-data-types/15-map-set-weakmap-weakset/2-recipients-set/task.md b/1-js/5-data-types/07-map-set-weakmap-weakset/2-recipients-set/task.md similarity index 100% rename from 1-js/4-data-types/15-map-set-weakmap-weakset/2-recipients-set/task.md rename to 1-js/5-data-types/07-map-set-weakmap-weakset/2-recipients-set/task.md diff --git a/1-js/4-data-types/15-map-set-weakmap-weakset/article.md b/1-js/5-data-types/07-map-set-weakmap-weakset/article.md similarity index 97% rename from 1-js/4-data-types/15-map-set-weakmap-weakset/article.md rename to 1-js/5-data-types/07-map-set-weakmap-weakset/article.md index 0bdca1f0..5219a86c 100644 --- a/1-js/4-data-types/15-map-set-weakmap-weakset/article.md +++ b/1-js/5-data-types/07-map-set-weakmap-weakset/article.md @@ -3,8 +3,8 @@ Now we know the following complex data structures: -- Objects for storing keyed collections -- Arrays for storing ordered collections +- Objects for storing keyed collections. +- Arrays for storing ordered collections. But that's not enough for real life. That's why there also exist `Map` and `Set`. @@ -95,8 +95,7 @@ map.set('1', 'str1') ## Map from Object - -When a `Map` is created, we can pass an array (or another iterable object) with key-value pairs, like this: +When a `Map` is created, we can pass an array (or another iterable) with key-value pairs, like this: ```js // array of [key, value] pairs @@ -122,9 +121,9 @@ Here, `Object.entries` returns the array of key/value pairs: `[ ["name","John"], For looping over a `map`, there are 3 methods: -- `map.keys()` -- returns an iterable object for keys, -- `map.values()` -- returns an iterable object for values, -- `map.entries()` -- returns an iterable object for entries `[key, value]`, it's used by default in `for..of`. +- `map.keys()` -- returns an iterable for keys, +- `map.values()` -- returns an iterable for values, +- `map.entries()` -- returns an iterable for entries `[key, value]`, it's used by default in `for..of`. For instance: diff --git a/1-js/4-data-types/19-json/1-serialize-object/solution.md b/1-js/5-data-types/08-json/1-serialize-object/solution.md similarity index 100% rename from 1-js/4-data-types/19-json/1-serialize-object/solution.md rename to 1-js/5-data-types/08-json/1-serialize-object/solution.md diff --git a/1-js/4-data-types/19-json/1-serialize-object/task.md b/1-js/5-data-types/08-json/1-serialize-object/task.md similarity index 100% rename from 1-js/4-data-types/19-json/1-serialize-object/task.md rename to 1-js/5-data-types/08-json/1-serialize-object/task.md diff --git a/1-js/4-data-types/19-json/2-serialize-object-circular/solution.md b/1-js/5-data-types/08-json/2-serialize-object-circular/solution.md similarity index 100% rename from 1-js/4-data-types/19-json/2-serialize-object-circular/solution.md rename to 1-js/5-data-types/08-json/2-serialize-object-circular/solution.md diff --git a/1-js/4-data-types/19-json/2-serialize-object-circular/task.md b/1-js/5-data-types/08-json/2-serialize-object-circular/task.md similarity index 100% rename from 1-js/4-data-types/19-json/2-serialize-object-circular/task.md rename to 1-js/5-data-types/08-json/2-serialize-object-circular/task.md diff --git a/1-js/4-data-types/19-json/article.md b/1-js/5-data-types/08-json/article.md similarity index 77% rename from 1-js/4-data-types/19-json/article.md rename to 1-js/5-data-types/08-json/article.md index e32ca279..bab55f91 100644 --- a/1-js/4-data-types/19-json/article.md +++ b/1-js/5-data-types/08-json/article.md @@ -26,9 +26,10 @@ let student = { let json = JSON.stringify(student); -alert(typeof json); // string +alert(typeof json); // we've got a string! + alert(json); -/* +/* JSON-encoded object: { "name": "John", "age": 30, @@ -41,8 +42,8 @@ alert(json); The JSON-encoded object has several important differences from the original variant: -- Strings use double quotes. No single quotes or backticks in JSON. So `'John'` became `"John"`. -- Object property names are double-quoted also. Also obligatory. So `name` became `"name"`. +- Strings use double quotes. No single quotes or backticks in JSON. So `'John'` becomes `"John"`. +- Object property names are double-quoted also. Also obligatory. So `age:30` becomes `"age":30`. `JSON.stringify` can be applied not only to objects, but to other values: @@ -72,7 +73,7 @@ The supported JSON types are: In the examples above we can see them all. -JSON format does not support any other values. +JSON format does not support any other types. For instance, functions and `undefined` values, symbolic properties are skipped by `JSON.stringify`: @@ -90,9 +91,7 @@ alert( JSON.stringify(user) ); // {} (empty object) ### Custom "toJSON" -Normally, an object is represented with a list of its properties. - -But it may provide its own JSON-transformation by implementing method `toJSON`. +If an object is not satisfied with the default behavior of `JSON.stringify`, it override it by implementing method `toJSON`. For instance: @@ -101,7 +100,7 @@ let room = { number: 23 }; -event = { +let event = { title: "Conference", date: new Date(Date.UTC(2017, 0, 1)), room @@ -119,84 +118,87 @@ alert( JSON.stringify(event) ); */ ``` -Please note that `date` `(1)` became a string. That's because all dates have a built-in `toJSON` method. +Here we can see that `date` `(1)` became a string. That's because all dates have a built-in `toJSON` method which returns such kind of string. +Now let's add a custom `toJSON` for our object `room`: -Обратим внимание на два момента: +```js run +let room = { + number: 23, +*!* + toJSON() { + return this.number; + } +*/!* +}; -1. Дата превратилась в строку. Это не случайно: у всех дат есть встроенный метод `toJSON`. Его результат в данном случае -- строка в таймзоне UTC. -2. У объекта `room` нет метода `toJSON`. Поэтому он сериализуется перечислением свойств. +let event = { + title: "Conference", + room +}; - Мы, конечно, могли бы добавить такой метод, тогда в итог попал бы его результат: +*!* +alert( JSON.stringify(room) ); // 23 +*/!* - ```js run - var room = { - number: 23, - *!* - toJSON: function() { - return this.number; - } - */!* - }; +alert( JSON.stringify(event) ); +/* + { + "title":"Conference", +*!* + "room": 23 +*/!* + } +*/ +``` - alert( JSON.stringify(room) ); // 23 - ``` +As we can see, `toJSON` is used both for the direct call `JSON.stringify(room)` and for the nested object. - - - -If our object wants to provide its own logic for JSON conversion TOJSON - - -The result of `JSON.stringify` is a string. We can send it over the wire or put in the plain data storage. - -To turn a JSON-string back into the object, we need another method named [JSON.parse](mdn:js/JSON/parse). - ## JSON.parse -Вызов `JSON.parse(str)` превратит строку с данными в формате JSON в JavaScript-объект/массив/значение. +To decode a JSON-string, we need another method named [JSON.parse](mdn:js/JSON/parse). -Например: +For instance: ```js run -var numbers = "[0, 1, 2, 3]"; +// stringified array +let numbers = "[0, 1, 2, 3]"; numbers = JSON.parse(numbers); alert( numbers[1] ); // 1 ``` -Или так: +Or for nested objects: ```js run -var user = '{ "name": "Вася", "age": 35, "isAdmin": false, "friends": [0,1,2,3] }'; +let user = '{ "name": "John", "age": 35, "isAdmin": false, "friends": [0,1,2,3] }'; user = JSON.parse(user); alert( user.friends[1] ); // 1 ``` -Данные могут быть сколь угодно сложными, объекты и массивы могут включать в себя другие объекты и массивы. Главное чтобы они соответствовали формату. +The JSON may be as complex as necessary, objects and arrays can include other objects and arrays. But they must obey the format. -````warn header="JSON-объекты ≠ JavaScript-объекты" -Объекты в формате JSON похожи на обычные JavaScript-объекты, но отличаются от них более строгими требованиями к строкам -- они должны быть именно в двойных кавычках. - -В частности, первые два свойства объекта ниже -- некорректны: +Here are typical mistakes of novice developers who try to write custom JSON manually (for debugging purposes mainly): ```js -{ - *!*name*/!*: "Вася", // ошибка: ключ name без кавычек! - "surname": *!*'Петров'*/!*,// ошибка: одинарные кавычки у значения 'Петров'! - "age": 35, // .. а тут всё в порядке. - "isAdmin": false // и тут тоже всё ок -} +let json = `{ + *!*name*/!*: "John", // mistake: property name without quotes + "surname": *!*'Smith'*/!*, // mistake: single quotes in value (must be double) + *!*'isAdmin'*/!*: false // mistake: single quotes in key (must be double) + "birthday": *!*new Date(2000, 2, 3)*/!*, // mistake: no "new" is allowed, only bare values + "friends": [0,1,2,3] // here all fine +}`; ``` -Кроме того, в формате JSON не поддерживаются комментарии. Он предназначен только для передачи данных. +Besides, JSON does not support comments. Adding a comment to JSON makes it invalid. -Есть нестандартное расширение формата JSON, которое называется [JSON5](http://json5.org/) и как раз разрешает ключи без кавычек, комментарии и т.п, как в обычном JavaScript. На данном этапе, это отдельная библиотека. -```` +There's another format named [JSON5](http://json5.org/), which allows unquoted keys, comments etc. But this is a standalone library, not in the specification of the language. + +The regular JSON is that strict not because its developers are lazy, but to allow easy, reliable and very fast implementations of the parsing algorithm. ## Умный разбор: JSON.parse(str, reviver) diff --git a/1-js/4-data-types/index.md b/1-js/5-data-types/index.md similarity index 100% rename from 1-js/4-data-types/index.md rename to 1-js/5-data-types/index.md diff --git a/1-js/6-data-types2/03-object2/article.md b/1-js/6-data-types2/03-object2/article.md deleted file mode 100644 index 6cabf891..00000000 --- a/1-js/6-data-types2/03-object2/article.md +++ /dev/null @@ -1,33 +0,0 @@ - - -# Property descriptors - -An object property is actually a more complex and tunable thing than just a "key-value" mapping. - -There are two kinds of properties. - -The first is *data properties*. All properties that we've seen yet are data properties. - -Data properties have a `value` and three special attributes: - -- **`writable`** -- if `true`, can be changed, otherwise it's read-only. -- **`enumerable`** -- if `true`, then listed in loops, otherwise not listed. -- **`configurable`** -- if `true`, the property can be deleted and these attributes can be modified, otherwise not. - -By default when a property is created, all attributes are `true`. - -We can get the the information about an existing property using [Object.getOwnPropertyDescriptor](mdn:js/Object/getOwnPropertyDescriptor): - - -```js run -let user = { - name: "John" -}; - -let descriptor = Object.getOwnPropertyDescriptor(user, 'name'); - -alert( descriptor.value ); // John -alert( descriptor.writable ); // true -alert( descriptor.enumerable ); // true -alert( descriptor.configurable ); // true -``` \ No newline at end of file diff --git a/1-js/6-data-types2/index.md b/1-js/6-data-types2/index.md deleted file mode 100644 index 246e2bc9..00000000 --- a/1-js/6-data-types2/index.md +++ /dev/null @@ -1,3 +0,0 @@ -# Data types - -More data structures and more in-depth study of the types. diff --git a/1-js/5-more-syntax/1-function-arguments-rest-spread/article.md b/1-js/6-more-syntax/1-function-arguments-rest-spread/article.md similarity index 100% rename from 1-js/5-more-syntax/1-function-arguments-rest-spread/article.md rename to 1-js/6-more-syntax/1-function-arguments-rest-spread/article.md diff --git a/1-js/5-more-syntax/2-destructuring-assignment/1-destructuring-assignment/solution.md b/1-js/6-more-syntax/2-destructuring-assignment/1-destructuring-assignment/solution.md similarity index 100% rename from 1-js/5-more-syntax/2-destructuring-assignment/1-destructuring-assignment/solution.md rename to 1-js/6-more-syntax/2-destructuring-assignment/1-destructuring-assignment/solution.md diff --git a/1-js/5-more-syntax/2-destructuring-assignment/1-destructuring-assignment/task.md b/1-js/6-more-syntax/2-destructuring-assignment/1-destructuring-assignment/task.md similarity index 100% rename from 1-js/5-more-syntax/2-destructuring-assignment/1-destructuring-assignment/task.md rename to 1-js/6-more-syntax/2-destructuring-assignment/1-destructuring-assignment/task.md diff --git a/1-js/5-more-syntax/2-destructuring-assignment/article.md b/1-js/6-more-syntax/2-destructuring-assignment/article.md similarity index 100% rename from 1-js/5-more-syntax/2-destructuring-assignment/article.md rename to 1-js/6-more-syntax/2-destructuring-assignment/article.md diff --git a/1-js/5-more-syntax/2-destructuring-assignment/destructuring-complex.png b/1-js/6-more-syntax/2-destructuring-assignment/destructuring-complex.png similarity index 100% rename from 1-js/5-more-syntax/2-destructuring-assignment/destructuring-complex.png rename to 1-js/6-more-syntax/2-destructuring-assignment/destructuring-complex.png diff --git a/1-js/5-more-syntax/2-destructuring-assignment/destructuring-complex@2x.png b/1-js/6-more-syntax/2-destructuring-assignment/destructuring-complex@2x.png similarity index 100% rename from 1-js/5-more-syntax/2-destructuring-assignment/destructuring-complex@2x.png rename to 1-js/6-more-syntax/2-destructuring-assignment/destructuring-complex@2x.png diff --git a/1-js/5-more-syntax/3-advanced-loops/1-iterable-keys/solution.md b/1-js/6-more-syntax/3-advanced-loops/1-iterable-keys/solution.md similarity index 100% rename from 1-js/5-more-syntax/3-advanced-loops/1-iterable-keys/solution.md rename to 1-js/6-more-syntax/3-advanced-loops/1-iterable-keys/solution.md diff --git a/1-js/5-more-syntax/3-advanced-loops/1-iterable-keys/task.md b/1-js/6-more-syntax/3-advanced-loops/1-iterable-keys/task.md similarity index 100% rename from 1-js/5-more-syntax/3-advanced-loops/1-iterable-keys/task.md rename to 1-js/6-more-syntax/3-advanced-loops/1-iterable-keys/task.md diff --git a/1-js/5-more-syntax/3-advanced-loops/5-sum-salaries/_js.view/solution.js b/1-js/6-more-syntax/3-advanced-loops/5-sum-salaries/_js.view/solution.js similarity index 100% rename from 1-js/5-more-syntax/3-advanced-loops/5-sum-salaries/_js.view/solution.js rename to 1-js/6-more-syntax/3-advanced-loops/5-sum-salaries/_js.view/solution.js diff --git a/1-js/5-more-syntax/3-advanced-loops/5-sum-salaries/_js.view/test.js b/1-js/6-more-syntax/3-advanced-loops/5-sum-salaries/_js.view/test.js similarity index 100% rename from 1-js/5-more-syntax/3-advanced-loops/5-sum-salaries/_js.view/test.js rename to 1-js/6-more-syntax/3-advanced-loops/5-sum-salaries/_js.view/test.js diff --git a/1-js/5-more-syntax/3-advanced-loops/5-sum-salaries/solution.md b/1-js/6-more-syntax/3-advanced-loops/5-sum-salaries/solution.md similarity index 100% rename from 1-js/5-more-syntax/3-advanced-loops/5-sum-salaries/solution.md rename to 1-js/6-more-syntax/3-advanced-loops/5-sum-salaries/solution.md diff --git a/1-js/5-more-syntax/3-advanced-loops/5-sum-salaries/task.md b/1-js/6-more-syntax/3-advanced-loops/5-sum-salaries/task.md similarity index 100% rename from 1-js/5-more-syntax/3-advanced-loops/5-sum-salaries/task.md rename to 1-js/6-more-syntax/3-advanced-loops/5-sum-salaries/task.md diff --git a/1-js/5-more-syntax/3-advanced-loops/6-max-salary/_js.view/solution.js b/1-js/6-more-syntax/3-advanced-loops/6-max-salary/_js.view/solution.js similarity index 100% rename from 1-js/5-more-syntax/3-advanced-loops/6-max-salary/_js.view/solution.js rename to 1-js/6-more-syntax/3-advanced-loops/6-max-salary/_js.view/solution.js diff --git a/1-js/5-more-syntax/3-advanced-loops/6-max-salary/_js.view/test.js b/1-js/6-more-syntax/3-advanced-loops/6-max-salary/_js.view/test.js similarity index 100% rename from 1-js/5-more-syntax/3-advanced-loops/6-max-salary/_js.view/test.js rename to 1-js/6-more-syntax/3-advanced-loops/6-max-salary/_js.view/test.js diff --git a/1-js/5-more-syntax/3-advanced-loops/6-max-salary/solution.md b/1-js/6-more-syntax/3-advanced-loops/6-max-salary/solution.md similarity index 100% rename from 1-js/5-more-syntax/3-advanced-loops/6-max-salary/solution.md rename to 1-js/6-more-syntax/3-advanced-loops/6-max-salary/solution.md diff --git a/1-js/5-more-syntax/3-advanced-loops/6-max-salary/task.md b/1-js/6-more-syntax/3-advanced-loops/6-max-salary/task.md similarity index 100% rename from 1-js/5-more-syntax/3-advanced-loops/6-max-salary/task.md rename to 1-js/6-more-syntax/3-advanced-loops/6-max-salary/task.md diff --git a/1-js/5-more-syntax/3-advanced-loops/7-count-properties/_js.view/solution.js b/1-js/6-more-syntax/3-advanced-loops/7-count-properties/_js.view/solution.js similarity index 100% rename from 1-js/5-more-syntax/3-advanced-loops/7-count-properties/_js.view/solution.js rename to 1-js/6-more-syntax/3-advanced-loops/7-count-properties/_js.view/solution.js diff --git a/1-js/5-more-syntax/3-advanced-loops/7-count-properties/_js.view/test.js b/1-js/6-more-syntax/3-advanced-loops/7-count-properties/_js.view/test.js similarity index 100% rename from 1-js/5-more-syntax/3-advanced-loops/7-count-properties/_js.view/test.js rename to 1-js/6-more-syntax/3-advanced-loops/7-count-properties/_js.view/test.js diff --git a/1-js/5-more-syntax/3-advanced-loops/7-count-properties/solution.md b/1-js/6-more-syntax/3-advanced-loops/7-count-properties/solution.md similarity index 100% rename from 1-js/5-more-syntax/3-advanced-loops/7-count-properties/solution.md rename to 1-js/6-more-syntax/3-advanced-loops/7-count-properties/solution.md diff --git a/1-js/5-more-syntax/3-advanced-loops/7-count-properties/task.md b/1-js/6-more-syntax/3-advanced-loops/7-count-properties/task.md similarity index 100% rename from 1-js/5-more-syntax/3-advanced-loops/7-count-properties/task.md rename to 1-js/6-more-syntax/3-advanced-loops/7-count-properties/task.md diff --git a/1-js/5-more-syntax/3-advanced-loops/article.md b/1-js/6-more-syntax/3-advanced-loops/article.md similarity index 86% rename from 1-js/5-more-syntax/3-advanced-loops/article.md rename to 1-js/6-more-syntax/3-advanced-loops/article.md index 79d9acc7..a28ba3ab 100644 --- a/1-js/5-more-syntax/3-advanced-loops/article.md +++ b/1-js/6-more-syntax/3-advanced-loops/article.md @@ -1,8 +1,7 @@ # Advanced loops -Now as we know arrays, iterables and destructuring, we're ready to understand cover few more forms of loops. - +Now as we know arrays, iterables and destructuring, we're ready to cover more forms of loops. ## Over objects @@ -136,10 +135,28 @@ alert(`Length: ${arr.length}`); // 5, remember, length is the last index + 1 ```` +## Over Sets, Maps... + +As we've seen in the chapter , `Map` and `Set` also implement methods `keys()`, `values()` and `entries()`. + +So we can iterate over them the same way. + +For instance, key/value iteration over a map: + +```js run +let recipeMap = new Map([ + ['cucumber', 500], + ['tomatoes', 350], + ['onion', 50] +]); + +for(let [key, value] of recipeMap) { // the same as of recipeMap.entries() + alert(key); // cucumber + alert(value); // 500 + // .. and so on +} +``` + ## Summary [todo] -Futher in the chapter we will meet other data structures `Map` and `Set` that also implement methods `keys()`, `values()` and `entries()`. - - - - +keys/values/entries are generic for collections \ No newline at end of file diff --git a/1-js/5-more-syntax/index.md b/1-js/6-more-syntax/index.md similarity index 100% rename from 1-js/5-more-syntax/index.md rename to 1-js/6-more-syntax/index.md diff --git a/1-js/7-deeper/1-recursion/1-sum-to/solution.md b/1-js/8-deeper/1-recursion/1-sum-to/solution.md similarity index 100% rename from 1-js/7-deeper/1-recursion/1-sum-to/solution.md rename to 1-js/8-deeper/1-recursion/1-sum-to/solution.md diff --git a/1-js/7-deeper/1-recursion/1-sum-to/task.md b/1-js/8-deeper/1-recursion/1-sum-to/task.md similarity index 100% rename from 1-js/7-deeper/1-recursion/1-sum-to/task.md rename to 1-js/8-deeper/1-recursion/1-sum-to/task.md diff --git a/1-js/7-deeper/1-recursion/2-factorial/solution.md b/1-js/8-deeper/1-recursion/2-factorial/solution.md similarity index 100% rename from 1-js/7-deeper/1-recursion/2-factorial/solution.md rename to 1-js/8-deeper/1-recursion/2-factorial/solution.md diff --git a/1-js/7-deeper/1-recursion/2-factorial/task.md b/1-js/8-deeper/1-recursion/2-factorial/task.md similarity index 100% rename from 1-js/7-deeper/1-recursion/2-factorial/task.md rename to 1-js/8-deeper/1-recursion/2-factorial/task.md diff --git a/1-js/7-deeper/1-recursion/3-fibonacci-numbers/solution.md b/1-js/8-deeper/1-recursion/3-fibonacci-numbers/solution.md similarity index 100% rename from 1-js/7-deeper/1-recursion/3-fibonacci-numbers/solution.md rename to 1-js/8-deeper/1-recursion/3-fibonacci-numbers/solution.md diff --git a/1-js/7-deeper/1-recursion/3-fibonacci-numbers/task.md b/1-js/8-deeper/1-recursion/3-fibonacci-numbers/task.md similarity index 100% rename from 1-js/7-deeper/1-recursion/3-fibonacci-numbers/task.md rename to 1-js/8-deeper/1-recursion/3-fibonacci-numbers/task.md diff --git a/1-js/7-deeper/1-recursion/9-output-single-linked-list/solution.md b/1-js/8-deeper/1-recursion/9-output-single-linked-list/solution.md similarity index 100% rename from 1-js/7-deeper/1-recursion/9-output-single-linked-list/solution.md rename to 1-js/8-deeper/1-recursion/9-output-single-linked-list/solution.md diff --git a/1-js/7-deeper/1-recursion/9-output-single-linked-list/task.md b/1-js/8-deeper/1-recursion/9-output-single-linked-list/task.md similarity index 100% rename from 1-js/7-deeper/1-recursion/9-output-single-linked-list/task.md rename to 1-js/8-deeper/1-recursion/9-output-single-linked-list/task.md diff --git a/1-js/7-deeper/1-recursion/article.md b/1-js/8-deeper/1-recursion/article.md similarity index 100% rename from 1-js/7-deeper/1-recursion/article.md rename to 1-js/8-deeper/1-recursion/article.md diff --git a/1-js/7-deeper/1-recursion/head.html b/1-js/8-deeper/1-recursion/head.html similarity index 100% rename from 1-js/7-deeper/1-recursion/head.html rename to 1-js/8-deeper/1-recursion/head.html diff --git a/1-js/7-deeper/1-recursion/linked-list-0.png b/1-js/8-deeper/1-recursion/linked-list-0.png similarity index 100% rename from 1-js/7-deeper/1-recursion/linked-list-0.png rename to 1-js/8-deeper/1-recursion/linked-list-0.png diff --git a/1-js/7-deeper/1-recursion/linked-list-0@2x.png b/1-js/8-deeper/1-recursion/linked-list-0@2x.png similarity index 100% rename from 1-js/7-deeper/1-recursion/linked-list-0@2x.png rename to 1-js/8-deeper/1-recursion/linked-list-0@2x.png diff --git a/1-js/7-deeper/1-recursion/linked-list-remove-1.png b/1-js/8-deeper/1-recursion/linked-list-remove-1.png similarity index 100% rename from 1-js/7-deeper/1-recursion/linked-list-remove-1.png rename to 1-js/8-deeper/1-recursion/linked-list-remove-1.png diff --git a/1-js/7-deeper/1-recursion/linked-list-remove-1@2x.png b/1-js/8-deeper/1-recursion/linked-list-remove-1@2x.png similarity index 100% rename from 1-js/7-deeper/1-recursion/linked-list-remove-1@2x.png rename to 1-js/8-deeper/1-recursion/linked-list-remove-1@2x.png diff --git a/1-js/7-deeper/1-recursion/linked-list-split.png b/1-js/8-deeper/1-recursion/linked-list-split.png similarity index 100% rename from 1-js/7-deeper/1-recursion/linked-list-split.png rename to 1-js/8-deeper/1-recursion/linked-list-split.png diff --git a/1-js/7-deeper/1-recursion/linked-list-split@2x.png b/1-js/8-deeper/1-recursion/linked-list-split@2x.png similarity index 100% rename from 1-js/7-deeper/1-recursion/linked-list-split@2x.png rename to 1-js/8-deeper/1-recursion/linked-list-split@2x.png diff --git a/1-js/7-deeper/1-recursion/linked-list.png b/1-js/8-deeper/1-recursion/linked-list.png similarity index 100% rename from 1-js/7-deeper/1-recursion/linked-list.png rename to 1-js/8-deeper/1-recursion/linked-list.png diff --git a/1-js/7-deeper/1-recursion/linked-list@2x.png b/1-js/8-deeper/1-recursion/linked-list@2x.png similarity index 100% rename from 1-js/7-deeper/1-recursion/linked-list@2x.png rename to 1-js/8-deeper/1-recursion/linked-list@2x.png diff --git a/1-js/7-deeper/1-recursion/recursion-pow.png b/1-js/8-deeper/1-recursion/recursion-pow.png similarity index 100% rename from 1-js/7-deeper/1-recursion/recursion-pow.png rename to 1-js/8-deeper/1-recursion/recursion-pow.png diff --git a/1-js/7-deeper/1-recursion/recursion-pow@2x.png b/1-js/8-deeper/1-recursion/recursion-pow@2x.png similarity index 100% rename from 1-js/7-deeper/1-recursion/recursion-pow@2x.png rename to 1-js/8-deeper/1-recursion/recursion-pow@2x.png diff --git a/1-js/7-deeper/1-recursion/recursive-salaries.png b/1-js/8-deeper/1-recursion/recursive-salaries.png similarity index 100% rename from 1-js/7-deeper/1-recursion/recursive-salaries.png rename to 1-js/8-deeper/1-recursion/recursive-salaries.png diff --git a/1-js/7-deeper/1-recursion/recursive-salaries@2x.png b/1-js/8-deeper/1-recursion/recursive-salaries@2x.png similarity index 100% rename from 1-js/7-deeper/1-recursion/recursive-salaries@2x.png rename to 1-js/8-deeper/1-recursion/recursive-salaries@2x.png diff --git a/1-js/7-deeper/2-closure/1-counter-independent/solution.md b/1-js/8-deeper/2-closure/1-counter-independent/solution.md similarity index 100% rename from 1-js/7-deeper/2-closure/1-counter-independent/solution.md rename to 1-js/8-deeper/2-closure/1-counter-independent/solution.md diff --git a/1-js/7-deeper/2-closure/1-counter-independent/task.md b/1-js/8-deeper/2-closure/1-counter-independent/task.md similarity index 100% rename from 1-js/7-deeper/2-closure/1-counter-independent/task.md rename to 1-js/8-deeper/2-closure/1-counter-independent/task.md diff --git a/1-js/7-deeper/2-closure/3-function-in-if/solution.md b/1-js/8-deeper/2-closure/3-function-in-if/solution.md similarity index 100% rename from 1-js/7-deeper/2-closure/3-function-in-if/solution.md rename to 1-js/8-deeper/2-closure/3-function-in-if/solution.md diff --git a/1-js/7-deeper/2-closure/3-function-in-if/task.md b/1-js/8-deeper/2-closure/3-function-in-if/task.md similarity index 100% rename from 1-js/7-deeper/2-closure/3-function-in-if/task.md rename to 1-js/8-deeper/2-closure/3-function-in-if/task.md diff --git a/1-js/7-deeper/2-closure/4-closure-sum/solution.md b/1-js/8-deeper/2-closure/4-closure-sum/solution.md similarity index 100% rename from 1-js/7-deeper/2-closure/4-closure-sum/solution.md rename to 1-js/8-deeper/2-closure/4-closure-sum/solution.md diff --git a/1-js/7-deeper/2-closure/4-closure-sum/task.md b/1-js/8-deeper/2-closure/4-closure-sum/task.md similarity index 100% rename from 1-js/7-deeper/2-closure/4-closure-sum/task.md rename to 1-js/8-deeper/2-closure/4-closure-sum/task.md diff --git a/1-js/7-deeper/2-closure/6-filter-through-function/_js.view/solution.js b/1-js/8-deeper/2-closure/6-filter-through-function/_js.view/solution.js similarity index 100% rename from 1-js/7-deeper/2-closure/6-filter-through-function/_js.view/solution.js rename to 1-js/8-deeper/2-closure/6-filter-through-function/_js.view/solution.js diff --git a/1-js/7-deeper/2-closure/6-filter-through-function/_js.view/source.js b/1-js/8-deeper/2-closure/6-filter-through-function/_js.view/source.js similarity index 100% rename from 1-js/7-deeper/2-closure/6-filter-through-function/_js.view/source.js rename to 1-js/8-deeper/2-closure/6-filter-through-function/_js.view/source.js diff --git a/1-js/7-deeper/2-closure/6-filter-through-function/_js.view/test.js b/1-js/8-deeper/2-closure/6-filter-through-function/_js.view/test.js similarity index 100% rename from 1-js/7-deeper/2-closure/6-filter-through-function/_js.view/test.js rename to 1-js/8-deeper/2-closure/6-filter-through-function/_js.view/test.js diff --git a/1-js/7-deeper/2-closure/6-filter-through-function/solution.md b/1-js/8-deeper/2-closure/6-filter-through-function/solution.md similarity index 100% rename from 1-js/7-deeper/2-closure/6-filter-through-function/solution.md rename to 1-js/8-deeper/2-closure/6-filter-through-function/solution.md diff --git a/1-js/7-deeper/2-closure/6-filter-through-function/task.md b/1-js/8-deeper/2-closure/6-filter-through-function/task.md similarity index 100% rename from 1-js/7-deeper/2-closure/6-filter-through-function/task.md rename to 1-js/8-deeper/2-closure/6-filter-through-function/task.md diff --git a/1-js/7-deeper/2-closure/7-sort-by-field/solution.md b/1-js/8-deeper/2-closure/7-sort-by-field/solution.md similarity index 100% rename from 1-js/7-deeper/2-closure/7-sort-by-field/solution.md rename to 1-js/8-deeper/2-closure/7-sort-by-field/solution.md diff --git a/1-js/7-deeper/2-closure/7-sort-by-field/task.md b/1-js/8-deeper/2-closure/7-sort-by-field/task.md similarity index 100% rename from 1-js/7-deeper/2-closure/7-sort-by-field/task.md rename to 1-js/8-deeper/2-closure/7-sort-by-field/task.md diff --git a/1-js/7-deeper/2-closure/8-make-army/_js.view/solution.js b/1-js/8-deeper/2-closure/8-make-army/_js.view/solution.js similarity index 100% rename from 1-js/7-deeper/2-closure/8-make-army/_js.view/solution.js rename to 1-js/8-deeper/2-closure/8-make-army/_js.view/solution.js diff --git a/1-js/7-deeper/2-closure/8-make-army/_js.view/source.js b/1-js/8-deeper/2-closure/8-make-army/_js.view/source.js similarity index 100% rename from 1-js/7-deeper/2-closure/8-make-army/_js.view/source.js rename to 1-js/8-deeper/2-closure/8-make-army/_js.view/source.js diff --git a/1-js/7-deeper/2-closure/8-make-army/_js.view/test.js b/1-js/8-deeper/2-closure/8-make-army/_js.view/test.js similarity index 100% rename from 1-js/7-deeper/2-closure/8-make-army/_js.view/test.js rename to 1-js/8-deeper/2-closure/8-make-army/_js.view/test.js diff --git a/1-js/7-deeper/2-closure/8-make-army/lexenv-makearmy.png b/1-js/8-deeper/2-closure/8-make-army/lexenv-makearmy.png similarity index 100% rename from 1-js/7-deeper/2-closure/8-make-army/lexenv-makearmy.png rename to 1-js/8-deeper/2-closure/8-make-army/lexenv-makearmy.png diff --git a/1-js/7-deeper/2-closure/8-make-army/lexenv-makearmy@2x.png b/1-js/8-deeper/2-closure/8-make-army/lexenv-makearmy@2x.png similarity index 100% rename from 1-js/7-deeper/2-closure/8-make-army/lexenv-makearmy@2x.png rename to 1-js/8-deeper/2-closure/8-make-army/lexenv-makearmy@2x.png diff --git a/1-js/7-deeper/2-closure/8-make-army/solution.md b/1-js/8-deeper/2-closure/8-make-army/solution.md similarity index 100% rename from 1-js/7-deeper/2-closure/8-make-army/solution.md rename to 1-js/8-deeper/2-closure/8-make-army/solution.md diff --git a/1-js/7-deeper/2-closure/8-make-army/task.md b/1-js/8-deeper/2-closure/8-make-army/task.md similarity index 100% rename from 1-js/7-deeper/2-closure/8-make-army/task.md rename to 1-js/8-deeper/2-closure/8-make-army/task.md diff --git a/1-js/7-deeper/2-closure/article.md b/1-js/8-deeper/2-closure/article.md similarity index 100% rename from 1-js/7-deeper/2-closure/article.md rename to 1-js/8-deeper/2-closure/article.md diff --git a/1-js/7-deeper/2-closure/lexenv-if.png b/1-js/8-deeper/2-closure/lexenv-if.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexenv-if.png rename to 1-js/8-deeper/2-closure/lexenv-if.png diff --git a/1-js/7-deeper/2-closure/lexenv-if@2x.png b/1-js/8-deeper/2-closure/lexenv-if@2x.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexenv-if@2x.png rename to 1-js/8-deeper/2-closure/lexenv-if@2x.png diff --git a/1-js/7-deeper/2-closure/lexenv-nested-makecounter-1.png b/1-js/8-deeper/2-closure/lexenv-nested-makecounter-1.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexenv-nested-makecounter-1.png rename to 1-js/8-deeper/2-closure/lexenv-nested-makecounter-1.png diff --git a/1-js/7-deeper/2-closure/lexenv-nested-makecounter-1@2x.png b/1-js/8-deeper/2-closure/lexenv-nested-makecounter-1@2x.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexenv-nested-makecounter-1@2x.png rename to 1-js/8-deeper/2-closure/lexenv-nested-makecounter-1@2x.png diff --git a/1-js/7-deeper/2-closure/lexenv-nested-makecounter-2.png b/1-js/8-deeper/2-closure/lexenv-nested-makecounter-2.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexenv-nested-makecounter-2.png rename to 1-js/8-deeper/2-closure/lexenv-nested-makecounter-2.png diff --git a/1-js/7-deeper/2-closure/lexenv-nested-makecounter-2@2x.png b/1-js/8-deeper/2-closure/lexenv-nested-makecounter-2@2x.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexenv-nested-makecounter-2@2x.png rename to 1-js/8-deeper/2-closure/lexenv-nested-makecounter-2@2x.png diff --git a/1-js/7-deeper/2-closure/lexenv-nested-makecounter-3.png b/1-js/8-deeper/2-closure/lexenv-nested-makecounter-3.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexenv-nested-makecounter-3.png rename to 1-js/8-deeper/2-closure/lexenv-nested-makecounter-3.png diff --git a/1-js/7-deeper/2-closure/lexenv-nested-makecounter-3@2x.png b/1-js/8-deeper/2-closure/lexenv-nested-makecounter-3@2x.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexenv-nested-makecounter-3@2x.png rename to 1-js/8-deeper/2-closure/lexenv-nested-makecounter-3@2x.png diff --git a/1-js/7-deeper/2-closure/lexenv-nested-makecounter-4.png b/1-js/8-deeper/2-closure/lexenv-nested-makecounter-4.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexenv-nested-makecounter-4.png rename to 1-js/8-deeper/2-closure/lexenv-nested-makecounter-4.png diff --git a/1-js/7-deeper/2-closure/lexenv-nested-makecounter-4@2x.png b/1-js/8-deeper/2-closure/lexenv-nested-makecounter-4@2x.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexenv-nested-makecounter-4@2x.png rename to 1-js/8-deeper/2-closure/lexenv-nested-makecounter-4@2x.png diff --git a/1-js/7-deeper/2-closure/lexenv-nested-makecounter-5.png b/1-js/8-deeper/2-closure/lexenv-nested-makecounter-5.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexenv-nested-makecounter-5.png rename to 1-js/8-deeper/2-closure/lexenv-nested-makecounter-5.png diff --git a/1-js/7-deeper/2-closure/lexenv-nested-makecounter-5@2x.png b/1-js/8-deeper/2-closure/lexenv-nested-makecounter-5@2x.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexenv-nested-makecounter-5@2x.png rename to 1-js/8-deeper/2-closure/lexenv-nested-makecounter-5@2x.png diff --git a/1-js/7-deeper/2-closure/lexenv-nested-makecounter-6.png b/1-js/8-deeper/2-closure/lexenv-nested-makecounter-6.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexenv-nested-makecounter-6.png rename to 1-js/8-deeper/2-closure/lexenv-nested-makecounter-6.png diff --git a/1-js/7-deeper/2-closure/lexenv-nested-makecounter-6@2x.png b/1-js/8-deeper/2-closure/lexenv-nested-makecounter-6@2x.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexenv-nested-makecounter-6@2x.png rename to 1-js/8-deeper/2-closure/lexenv-nested-makecounter-6@2x.png diff --git a/1-js/7-deeper/2-closure/lexenv-nested-work.png b/1-js/8-deeper/2-closure/lexenv-nested-work.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexenv-nested-work.png rename to 1-js/8-deeper/2-closure/lexenv-nested-work.png diff --git a/1-js/7-deeper/2-closure/lexenv-nested-work@2x.png b/1-js/8-deeper/2-closure/lexenv-nested-work@2x.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexenv-nested-work@2x.png rename to 1-js/8-deeper/2-closure/lexenv-nested-work@2x.png diff --git a/1-js/7-deeper/2-closure/lexical-environment-global-2.png b/1-js/8-deeper/2-closure/lexical-environment-global-2.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexical-environment-global-2.png rename to 1-js/8-deeper/2-closure/lexical-environment-global-2.png diff --git a/1-js/7-deeper/2-closure/lexical-environment-global-2@2x.png b/1-js/8-deeper/2-closure/lexical-environment-global-2@2x.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexical-environment-global-2@2x.png rename to 1-js/8-deeper/2-closure/lexical-environment-global-2@2x.png diff --git a/1-js/7-deeper/2-closure/lexical-environment-global-3.png b/1-js/8-deeper/2-closure/lexical-environment-global-3.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexical-environment-global-3.png rename to 1-js/8-deeper/2-closure/lexical-environment-global-3.png diff --git a/1-js/7-deeper/2-closure/lexical-environment-global-3@2x.png b/1-js/8-deeper/2-closure/lexical-environment-global-3@2x.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexical-environment-global-3@2x.png rename to 1-js/8-deeper/2-closure/lexical-environment-global-3@2x.png diff --git a/1-js/7-deeper/2-closure/lexical-environment-global.png b/1-js/8-deeper/2-closure/lexical-environment-global.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexical-environment-global.png rename to 1-js/8-deeper/2-closure/lexical-environment-global.png diff --git a/1-js/7-deeper/2-closure/lexical-environment-global@2x.png b/1-js/8-deeper/2-closure/lexical-environment-global@2x.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexical-environment-global@2x.png rename to 1-js/8-deeper/2-closure/lexical-environment-global@2x.png diff --git a/1-js/7-deeper/2-closure/lexical-environment-simple-lookup.png b/1-js/8-deeper/2-closure/lexical-environment-simple-lookup.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexical-environment-simple-lookup.png rename to 1-js/8-deeper/2-closure/lexical-environment-simple-lookup.png diff --git a/1-js/7-deeper/2-closure/lexical-environment-simple-lookup@2x.png b/1-js/8-deeper/2-closure/lexical-environment-simple-lookup@2x.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexical-environment-simple-lookup@2x.png rename to 1-js/8-deeper/2-closure/lexical-environment-simple-lookup@2x.png diff --git a/1-js/7-deeper/2-closure/lexical-environment-simple.png b/1-js/8-deeper/2-closure/lexical-environment-simple.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexical-environment-simple.png rename to 1-js/8-deeper/2-closure/lexical-environment-simple.png diff --git a/1-js/7-deeper/2-closure/lexical-environment-simple@2x.png b/1-js/8-deeper/2-closure/lexical-environment-simple@2x.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexical-environment-simple@2x.png rename to 1-js/8-deeper/2-closure/lexical-environment-simple@2x.png diff --git a/1-js/7-deeper/2-closure/lexical-search-order.png b/1-js/8-deeper/2-closure/lexical-search-order.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexical-search-order.png rename to 1-js/8-deeper/2-closure/lexical-search-order.png diff --git a/1-js/7-deeper/2-closure/lexical-search-order@2x.png b/1-js/8-deeper/2-closure/lexical-search-order@2x.png similarity index 100% rename from 1-js/7-deeper/2-closure/lexical-search-order@2x.png rename to 1-js/8-deeper/2-closure/lexical-search-order@2x.png diff --git a/1-js/7-deeper/3-function-object/2-counter-inc-dec/_js.view/solution.js b/1-js/8-deeper/3-function-object/2-counter-inc-dec/_js.view/solution.js similarity index 100% rename from 1-js/7-deeper/3-function-object/2-counter-inc-dec/_js.view/solution.js rename to 1-js/8-deeper/3-function-object/2-counter-inc-dec/_js.view/solution.js diff --git a/1-js/7-deeper/3-function-object/2-counter-inc-dec/_js.view/source.js b/1-js/8-deeper/3-function-object/2-counter-inc-dec/_js.view/source.js similarity index 100% rename from 1-js/7-deeper/3-function-object/2-counter-inc-dec/_js.view/source.js rename to 1-js/8-deeper/3-function-object/2-counter-inc-dec/_js.view/source.js diff --git a/1-js/7-deeper/3-function-object/2-counter-inc-dec/_js.view/test.js b/1-js/8-deeper/3-function-object/2-counter-inc-dec/_js.view/test.js similarity index 100% rename from 1-js/7-deeper/3-function-object/2-counter-inc-dec/_js.view/test.js rename to 1-js/8-deeper/3-function-object/2-counter-inc-dec/_js.view/test.js diff --git a/1-js/7-deeper/3-function-object/2-counter-inc-dec/solution.md b/1-js/8-deeper/3-function-object/2-counter-inc-dec/solution.md similarity index 100% rename from 1-js/7-deeper/3-function-object/2-counter-inc-dec/solution.md rename to 1-js/8-deeper/3-function-object/2-counter-inc-dec/solution.md diff --git a/1-js/7-deeper/3-function-object/2-counter-inc-dec/task.md b/1-js/8-deeper/3-function-object/2-counter-inc-dec/task.md similarity index 100% rename from 1-js/7-deeper/3-function-object/2-counter-inc-dec/task.md rename to 1-js/8-deeper/3-function-object/2-counter-inc-dec/task.md diff --git a/1-js/7-deeper/3-function-object/5-sum-many-brackets/solution.md b/1-js/8-deeper/3-function-object/5-sum-many-brackets/solution.md similarity index 100% rename from 1-js/7-deeper/3-function-object/5-sum-many-brackets/solution.md rename to 1-js/8-deeper/3-function-object/5-sum-many-brackets/solution.md diff --git a/1-js/7-deeper/3-function-object/5-sum-many-brackets/task.md b/1-js/8-deeper/3-function-object/5-sum-many-brackets/task.md similarity index 100% rename from 1-js/7-deeper/3-function-object/5-sum-many-brackets/task.md rename to 1-js/8-deeper/3-function-object/5-sum-many-brackets/task.md diff --git a/1-js/7-deeper/3-function-object/article.md b/1-js/8-deeper/3-function-object/article.md similarity index 100% rename from 1-js/7-deeper/3-function-object/article.md rename to 1-js/8-deeper/3-function-object/article.md diff --git a/1-js/7-deeper/4-new-function/article.md b/1-js/8-deeper/4-new-function/article.md similarity index 100% rename from 1-js/7-deeper/4-new-function/article.md rename to 1-js/8-deeper/4-new-function/article.md diff --git a/1-js/7-deeper/5-settimeout-setinterval/1-output-numbers-100ms/solution.md b/1-js/8-deeper/5-settimeout-setinterval/1-output-numbers-100ms/solution.md similarity index 100% rename from 1-js/7-deeper/5-settimeout-setinterval/1-output-numbers-100ms/solution.md rename to 1-js/8-deeper/5-settimeout-setinterval/1-output-numbers-100ms/solution.md diff --git a/1-js/7-deeper/5-settimeout-setinterval/1-output-numbers-100ms/task.md b/1-js/8-deeper/5-settimeout-setinterval/1-output-numbers-100ms/task.md similarity index 100% rename from 1-js/7-deeper/5-settimeout-setinterval/1-output-numbers-100ms/task.md rename to 1-js/8-deeper/5-settimeout-setinterval/1-output-numbers-100ms/task.md diff --git a/1-js/7-deeper/5-settimeout-setinterval/3-rewrite-settimeout-0/solution.md b/1-js/8-deeper/5-settimeout-setinterval/3-rewrite-settimeout-0/solution.md similarity index 68% rename from 1-js/7-deeper/5-settimeout-setinterval/3-rewrite-settimeout-0/solution.md rename to 1-js/8-deeper/5-settimeout-setinterval/3-rewrite-settimeout-0/solution.md index 322c66a7..42a6a004 100644 --- a/1-js/7-deeper/5-settimeout-setinterval/3-rewrite-settimeout-0/solution.md +++ b/1-js/8-deeper/5-settimeout-setinterval/3-rewrite-settimeout-0/solution.md @@ -3,7 +3,7 @@ ```js run let i = 0; -let start = performance.now(); +let start = Date.now(); let timer = setInterval(count, 0); @@ -14,7 +14,7 @@ function count() { } if (i == 1000000000) { - alert("Done in " + (performance.now() - start) + 'ms'); + alert("Done in " + (Date.now() - start) + 'ms'); cancelInterval(timer); } diff --git a/1-js/7-deeper/5-settimeout-setinterval/3-rewrite-settimeout-0/task.md b/1-js/8-deeper/5-settimeout-setinterval/3-rewrite-settimeout-0/task.md similarity index 77% rename from 1-js/7-deeper/5-settimeout-setinterval/3-rewrite-settimeout-0/task.md rename to 1-js/8-deeper/5-settimeout-setinterval/3-rewrite-settimeout-0/task.md index bc208888..cc5c94a5 100644 --- a/1-js/7-deeper/5-settimeout-setinterval/3-rewrite-settimeout-0/task.md +++ b/1-js/8-deeper/5-settimeout-setinterval/3-rewrite-settimeout-0/task.md @@ -9,12 +9,12 @@ Rewrite the split counting function from setTimeout to setInterval: ```js run let i = 0; -let start = performance.now(); +let start = Date.now(); function count() { if (i == 1000000000) { - alert("Done in " + (performance.now() - start) + 'ms'); + alert("Done in " + (Date.now() - start) + 'ms'); } else { setTimeout(count, 0); } diff --git a/1-js/7-deeper/5-settimeout-setinterval/4-settimeout-result/solution.md b/1-js/8-deeper/5-settimeout-setinterval/4-settimeout-result/solution.md similarity index 100% rename from 1-js/7-deeper/5-settimeout-setinterval/4-settimeout-result/solution.md rename to 1-js/8-deeper/5-settimeout-setinterval/4-settimeout-result/solution.md diff --git a/1-js/7-deeper/5-settimeout-setinterval/4-settimeout-result/task.md b/1-js/8-deeper/5-settimeout-setinterval/4-settimeout-result/task.md similarity index 100% rename from 1-js/7-deeper/5-settimeout-setinterval/4-settimeout-result/task.md rename to 1-js/8-deeper/5-settimeout-setinterval/4-settimeout-result/task.md diff --git a/1-js/7-deeper/5-settimeout-setinterval/article.md b/1-js/8-deeper/5-settimeout-setinterval/article.md similarity index 97% rename from 1-js/7-deeper/5-settimeout-setinterval/article.md rename to 1-js/8-deeper/5-settimeout-setinterval/article.md index d639665c..61f3199d 100644 --- a/1-js/7-deeper/5-settimeout-setinterval/article.md +++ b/1-js/8-deeper/5-settimeout-setinterval/article.md @@ -248,7 +248,7 @@ If you run it, the CPU will hang. For server-side JS that's clearly noticeable, ```js run let i = 0; -let start = performance.now(); +let start = Date.now(); function count() { @@ -256,7 +256,7 @@ function count() { i++; } - alert("Done in " + (performance.now() - start) + 'ms'); + alert("Done in " + (Date.now() - start) + 'ms'); } count(); @@ -267,12 +267,12 @@ Now the split version: ```js run let i = 0; -let start = performance.now(); +let start = Date.now(); function count() { if (i == 1000000000) { - alert("Done in " + (performance.now() - start) + 'ms'); + alert("Done in " + (Date.now() - start) + 'ms'); } else { setTimeout(count, 0); } @@ -301,7 +301,7 @@ Here's the code with `setTimeout` at the end to compare: ```js run let i = 0; -let start = performance.now(); +let start = Date.now(); function count() { @@ -312,7 +312,7 @@ function count() { // moved to "after the job" *!* if (i == 1000000000) { - alert("Done in " + (performance.now() - start) + 'ms'); + alert("Done in " + (Date.now() - start) + 'ms'); } else { setTimeout(count, 0); } diff --git a/1-js/7-deeper/5-settimeout-setinterval/setinterval-interval.png b/1-js/8-deeper/5-settimeout-setinterval/setinterval-interval.png similarity index 100% rename from 1-js/7-deeper/5-settimeout-setinterval/setinterval-interval.png rename to 1-js/8-deeper/5-settimeout-setinterval/setinterval-interval.png diff --git a/1-js/7-deeper/5-settimeout-setinterval/setinterval-interval@2x.png b/1-js/8-deeper/5-settimeout-setinterval/setinterval-interval@2x.png similarity index 100% rename from 1-js/7-deeper/5-settimeout-setinterval/setinterval-interval@2x.png rename to 1-js/8-deeper/5-settimeout-setinterval/setinterval-interval@2x.png diff --git a/1-js/7-deeper/5-settimeout-setinterval/settimeout-interval.png b/1-js/8-deeper/5-settimeout-setinterval/settimeout-interval.png similarity index 100% rename from 1-js/7-deeper/5-settimeout-setinterval/settimeout-interval.png rename to 1-js/8-deeper/5-settimeout-setinterval/settimeout-interval.png diff --git a/1-js/7-deeper/5-settimeout-setinterval/settimeout-interval@2x.png b/1-js/8-deeper/5-settimeout-setinterval/settimeout-interval@2x.png similarity index 100% rename from 1-js/7-deeper/5-settimeout-setinterval/settimeout-interval@2x.png rename to 1-js/8-deeper/5-settimeout-setinterval/settimeout-interval@2x.png diff --git a/1-js/7-deeper/6-call-apply-decorators/2-spy-decorator/_js.view/solution.js b/1-js/8-deeper/6-call-apply-decorators/2-spy-decorator/_js.view/solution.js similarity index 100% rename from 1-js/7-deeper/6-call-apply-decorators/2-spy-decorator/_js.view/solution.js rename to 1-js/8-deeper/6-call-apply-decorators/2-spy-decorator/_js.view/solution.js diff --git a/1-js/7-deeper/6-call-apply-decorators/2-spy-decorator/_js.view/source.js b/1-js/8-deeper/6-call-apply-decorators/2-spy-decorator/_js.view/source.js similarity index 100% rename from 1-js/7-deeper/6-call-apply-decorators/2-spy-decorator/_js.view/source.js rename to 1-js/8-deeper/6-call-apply-decorators/2-spy-decorator/_js.view/source.js diff --git a/1-js/7-deeper/6-call-apply-decorators/2-spy-decorator/_js.view/test.js b/1-js/8-deeper/6-call-apply-decorators/2-spy-decorator/_js.view/test.js similarity index 100% rename from 1-js/7-deeper/6-call-apply-decorators/2-spy-decorator/_js.view/test.js rename to 1-js/8-deeper/6-call-apply-decorators/2-spy-decorator/_js.view/test.js diff --git a/1-js/7-deeper/6-call-apply-decorators/2-spy-decorator/solution.md b/1-js/8-deeper/6-call-apply-decorators/2-spy-decorator/solution.md similarity index 100% rename from 1-js/7-deeper/6-call-apply-decorators/2-spy-decorator/solution.md rename to 1-js/8-deeper/6-call-apply-decorators/2-spy-decorator/solution.md diff --git a/1-js/7-deeper/6-call-apply-decorators/2-spy-decorator/task.md b/1-js/8-deeper/6-call-apply-decorators/2-spy-decorator/task.md similarity index 100% rename from 1-js/7-deeper/6-call-apply-decorators/2-spy-decorator/task.md rename to 1-js/8-deeper/6-call-apply-decorators/2-spy-decorator/task.md diff --git a/1-js/7-deeper/6-call-apply-decorators/8-debounce/_js.view/solution.js b/1-js/8-deeper/6-call-apply-decorators/8-debounce/_js.view/solution.js similarity index 100% rename from 1-js/7-deeper/6-call-apply-decorators/8-debounce/_js.view/solution.js rename to 1-js/8-deeper/6-call-apply-decorators/8-debounce/_js.view/solution.js diff --git a/1-js/7-deeper/6-call-apply-decorators/8-debounce/_js.view/test.js b/1-js/8-deeper/6-call-apply-decorators/8-debounce/_js.view/test.js similarity index 100% rename from 1-js/7-deeper/6-call-apply-decorators/8-debounce/_js.view/test.js rename to 1-js/8-deeper/6-call-apply-decorators/8-debounce/_js.view/test.js diff --git a/1-js/7-deeper/6-call-apply-decorators/8-debounce/solution.md b/1-js/8-deeper/6-call-apply-decorators/8-debounce/solution.md similarity index 100% rename from 1-js/7-deeper/6-call-apply-decorators/8-debounce/solution.md rename to 1-js/8-deeper/6-call-apply-decorators/8-debounce/solution.md diff --git a/1-js/7-deeper/6-call-apply-decorators/8-debounce/task.md b/1-js/8-deeper/6-call-apply-decorators/8-debounce/task.md similarity index 100% rename from 1-js/7-deeper/6-call-apply-decorators/8-debounce/task.md rename to 1-js/8-deeper/6-call-apply-decorators/8-debounce/task.md diff --git a/1-js/7-deeper/6-call-apply-decorators/9-throttle/_js.view/solution.js b/1-js/8-deeper/6-call-apply-decorators/9-throttle/_js.view/solution.js similarity index 100% rename from 1-js/7-deeper/6-call-apply-decorators/9-throttle/_js.view/solution.js rename to 1-js/8-deeper/6-call-apply-decorators/9-throttle/_js.view/solution.js diff --git a/1-js/7-deeper/6-call-apply-decorators/9-throttle/_js.view/test.js b/1-js/8-deeper/6-call-apply-decorators/9-throttle/_js.view/test.js similarity index 100% rename from 1-js/7-deeper/6-call-apply-decorators/9-throttle/_js.view/test.js rename to 1-js/8-deeper/6-call-apply-decorators/9-throttle/_js.view/test.js diff --git a/1-js/7-deeper/6-call-apply-decorators/9-throttle/solution.md b/1-js/8-deeper/6-call-apply-decorators/9-throttle/solution.md similarity index 100% rename from 1-js/7-deeper/6-call-apply-decorators/9-throttle/solution.md rename to 1-js/8-deeper/6-call-apply-decorators/9-throttle/solution.md diff --git a/1-js/7-deeper/6-call-apply-decorators/9-throttle/task.md b/1-js/8-deeper/6-call-apply-decorators/9-throttle/task.md similarity index 100% rename from 1-js/7-deeper/6-call-apply-decorators/9-throttle/task.md rename to 1-js/8-deeper/6-call-apply-decorators/9-throttle/task.md diff --git a/1-js/7-deeper/6-call-apply-decorators/article.md b/1-js/8-deeper/6-call-apply-decorators/article.md similarity index 100% rename from 1-js/7-deeper/6-call-apply-decorators/article.md rename to 1-js/8-deeper/6-call-apply-decorators/article.md diff --git a/1-js/7-deeper/6-call-apply-decorators/decorator-makecaching-wrapper.png b/1-js/8-deeper/6-call-apply-decorators/decorator-makecaching-wrapper.png similarity index 100% rename from 1-js/7-deeper/6-call-apply-decorators/decorator-makecaching-wrapper.png rename to 1-js/8-deeper/6-call-apply-decorators/decorator-makecaching-wrapper.png diff --git a/1-js/7-deeper/6-call-apply-decorators/decorator-makecaching-wrapper@2x.png b/1-js/8-deeper/6-call-apply-decorators/decorator-makecaching-wrapper@2x.png similarity index 100% rename from 1-js/7-deeper/6-call-apply-decorators/decorator-makecaching-wrapper@2x.png rename to 1-js/8-deeper/6-call-apply-decorators/decorator-makecaching-wrapper@2x.png diff --git a/1-js/7-deeper/7-bind/2-write-to-object-after-bind/solution.md b/1-js/8-deeper/7-bind/2-write-to-object-after-bind/solution.md similarity index 100% rename from 1-js/7-deeper/7-bind/2-write-to-object-after-bind/solution.md rename to 1-js/8-deeper/7-bind/2-write-to-object-after-bind/solution.md diff --git a/1-js/7-deeper/7-bind/2-write-to-object-after-bind/task.md b/1-js/8-deeper/7-bind/2-write-to-object-after-bind/task.md similarity index 100% rename from 1-js/7-deeper/7-bind/2-write-to-object-after-bind/task.md rename to 1-js/8-deeper/7-bind/2-write-to-object-after-bind/task.md diff --git a/1-js/7-deeper/7-bind/3-second-bind/solution.md b/1-js/8-deeper/7-bind/3-second-bind/solution.md similarity index 100% rename from 1-js/7-deeper/7-bind/3-second-bind/solution.md rename to 1-js/8-deeper/7-bind/3-second-bind/solution.md diff --git a/1-js/7-deeper/7-bind/3-second-bind/task.md b/1-js/8-deeper/7-bind/3-second-bind/task.md similarity index 100% rename from 1-js/7-deeper/7-bind/3-second-bind/task.md rename to 1-js/8-deeper/7-bind/3-second-bind/task.md diff --git a/1-js/7-deeper/7-bind/4-function-property-after-bind/solution.md b/1-js/8-deeper/7-bind/4-function-property-after-bind/solution.md similarity index 100% rename from 1-js/7-deeper/7-bind/4-function-property-after-bind/solution.md rename to 1-js/8-deeper/7-bind/4-function-property-after-bind/solution.md diff --git a/1-js/7-deeper/7-bind/4-function-property-after-bind/task.md b/1-js/8-deeper/7-bind/4-function-property-after-bind/task.md similarity index 100% rename from 1-js/7-deeper/7-bind/4-function-property-after-bind/task.md rename to 1-js/8-deeper/7-bind/4-function-property-after-bind/task.md diff --git a/1-js/7-deeper/7-bind/5-question-use-bind/solution.md b/1-js/8-deeper/7-bind/5-question-use-bind/solution.md similarity index 100% rename from 1-js/7-deeper/7-bind/5-question-use-bind/solution.md rename to 1-js/8-deeper/7-bind/5-question-use-bind/solution.md diff --git a/1-js/7-deeper/7-bind/5-question-use-bind/task.md b/1-js/8-deeper/7-bind/5-question-use-bind/task.md similarity index 100% rename from 1-js/7-deeper/7-bind/5-question-use-bind/task.md rename to 1-js/8-deeper/7-bind/5-question-use-bind/task.md diff --git a/1-js/7-deeper/7-bind/6-ask-currying/solution.md b/1-js/8-deeper/7-bind/6-ask-currying/solution.md similarity index 100% rename from 1-js/7-deeper/7-bind/6-ask-currying/solution.md rename to 1-js/8-deeper/7-bind/6-ask-currying/solution.md diff --git a/1-js/7-deeper/7-bind/6-ask-currying/task.md b/1-js/8-deeper/7-bind/6-ask-currying/task.md similarity index 100% rename from 1-js/7-deeper/7-bind/6-ask-currying/task.md rename to 1-js/8-deeper/7-bind/6-ask-currying/task.md diff --git a/1-js/7-deeper/7-bind/article.md b/1-js/8-deeper/7-bind/article.md similarity index 100% rename from 1-js/7-deeper/7-bind/article.md rename to 1-js/8-deeper/7-bind/article.md diff --git a/1-js/7-deeper/7-bind/head.html b/1-js/8-deeper/7-bind/head.html similarity index 100% rename from 1-js/7-deeper/7-bind/head.html rename to 1-js/8-deeper/7-bind/head.html diff --git a/1-js/7-deeper/index.md b/1-js/8-deeper/index.md similarity index 100% rename from 1-js/7-deeper/index.md rename to 1-js/8-deeper/index.md diff --git a/1-js/plan3.txt b/1-js/plan3.txt index f0a12a0b..3a39292a 100644 --- a/1-js/plan3.txt +++ b/1-js/plan3.txt @@ -39,10 +39,12 @@ object-basics map-set-weakmap-weakset date (TODO: tasks) <<< json? + << intl more-syntax function-arguments-rest-spread destructuring-assignment (also func params destructuring) advanced-loops (iterators over objects, arrays) + << try..catch, rethrow using err.name deeper recursion running execution context = where + lexical environment = envrec + outer