React interview Flashcards

RU

1
Q

что такое Object.keys, Object.values, и Object.entries в JavaScript?

A

Object.keys(obj) — возвращает массив ключей объекта.
Object.values(obj) — возвращает массив значений объекта.
Object.entries(obj) — возвращает массив пар [ключ, значение] для каждого свойства объекта.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
2
Q

Что такое debounce и как он работает?

A

Когда функция обёрнута в debounce, она не выполняется сразу, а ждет некоторое время после последнего вызова. Если в течение этого времени происходит новый вызов, таймер сбрасывается, и функция снова ждет. Это особенно полезно для функций, которые могут вызываться часто, например, при вводе текста в поле или при прокрутке страницы.

function debounce(func, delay) {
let timer;
return function (…args) {
clearTimeout(timer);
timer = setTimeout(() => func.apply(this, args), delay);
};
}

// Использование
const debouncedFunc = debounce(() => console.log(‘Executed!’), 300);
debouncedFunc(); // Будет выполнено через 300 мс, если нет нового вызова

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
3
Q

Чем отличается var от let и const в JavaScript?

A

var:
Действительно, var имеет функциональную область видимости, а не блочную. Это значит, что он виден в функции, но не внутри блока (if, for и т.д.).
Поддерживает всплытие (hoisting), так что переменная как бы “поднимается” к началу своей области видимости.
let и const:
Блочная область видимости: они видны только внутри блока, в котором объявлены.
const — значение переменной нельзя переназначить (но если это объект, можно изменять его свойства).
let можно переназначить, но нельзя повторно объявить в той же области.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
4
Q

В чем разница между function declaration и function expression в JavaScript?

A

Function Declaration (объявление функции):

Записывается как function name() {}.
Выполняется до начала кода благодаря всплытию (hoisting), так что функция доступна во всем блоке, даже если вызвана до её объявления.
Function Expression (функциональное выражение):

Создается как часть выражения, например, let func = function() {} или const func = () => {}.
Не всплывает, так что доступна только после строки, где объявлена.
Итак, основные отличия: всплытие и доступность до инициализации.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
5
Q

Что такое CORS и зачем он нужен?

A

CORS (Cross-Origin Resource Sharing) — это механизм, который позволяет ограничить доступ к ресурсам на одном домене с веб-страниц, загруженных с другого домена.
По умолчанию браузеры блокируют такие запросы для защиты от потенциальных угроз.
Сервер может настроить CORS, добавляя специальные заголовки, чтобы разрешить доступ с определенных доменов.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
6
Q

Что такое async и defer в контексте загрузки скриптов в HTML?

A

async:

Скрипт загружается асинхронно, то есть не блокирует загрузку HTML-документа.
Выполняется сразу после загрузки, даже если HTML еще не полностью обработан. Это может привести к выполнению скрипта до завершения разбора документа.

defer:

Скрипт загружается асинхронно, но его выполнение откладывается до тех пор, пока весь HTML-документ не будет полностью разобран.
Подходит для скриптов, которые зависят от полной загрузки DOM.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
7
Q

Каковы основные виды хуков в React?

A

useState:

Хук, который позволяет добавлять состояние в функциональные компоненты. Возвращает массив с текущим состоянием и функцией для его обновления.

useEffect:

Используется для выполнения побочных эффектов в функциональных компонентах, таких как запросы к API или подписка на события. Срабатывает после рендеринга компонента и может быть настроен на выполнение при изменении зависимостей.

useMemo:

Позволяет запоминать результат функции и пересчитывать его только тогда, когда изменяются определенные зависимости. Это полезно для оптимизации производительности, когда есть дорогие вычисления.

useReducer
Хук для управления состоянием, похожий на useState, но более подходящий для сложных состояний или состояний, зависящих от предыдущего состояния.
Обычно используется с функциональными компонентами, где состояние может изменяться в зависимости от определенных действий.

useContext

Позволяет использовать контекст API, чтобы передавать данные через дерево компонентов, не передавая их явно через props.
Упрощает работу с глобальным состоянием или данными, которые могут использоваться в разных компонентах.

useRef

Возвращает изменяемый объект, который сохраняет .current свойство. Обычно используется для доступа к DOM-элементам или хранения изменяемых значений, которые не требуют перерисовки компонента.
Полезен для работы с элементами ввода, анимациями и интеграцией с библиотеками.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
8
Q

Что такое мемоизация?

A

Мемоизация — это оптимизационная техника, которая сохраняет результаты вызовов функции и возвращает кэшированный результат, когда те же входные параметры передаются снова.
Это помогает избежать лишних вычислений и повышает производительность, особенно для дорогих по времени операций.

В React:
useMemo: Используется для мемоизации вычисленных значений.
useCallback: Мемоизирует функции, предотвращая их пересоздание при каждом рендере.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
9
Q

Что такое рекурсия и как она работает в JavaScript?

A

Рекурсия — это метод решения задач, при котором функция вызывает саму себя для выполнения подзадач. В JavaScript рекурсия может использоваться для обработки структур данных, таких как деревья или для решения задач, которые могут быть разбиты на более мелкие, схожие задачи, например, вычисление факториала. Важно помнить о базовом случае, который останавливает рекурсию, чтобы избежать бесконечного цикла.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
9
Q

Что такое query-селекторы и как они используются в JavaScript?

A

Query-селекторы — это методы, позволяющие выбирать элементы из DOM по различным критериям. В JavaScript используются методы document.querySelector и document.querySelectorAll. querySelector возвращает первый найденный элемент, соответствующий указанному селектору, тогда как querySelectorAll возвращает все подходящие элементы в виде NodeList. Эти методы поддерживают различные CSS-селекторы, что позволяет разработчикам эффективно находить и манипулировать элементами на странице.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
10
Q

Какие основные методы массивов доступны в JavaScript и для чего они используются?

A

JavaScript предоставляет множество методов для работы с массивами. К основным из них относятся map, filter, reduce, forEach, push, pop, shift и unshift. Метод map создает новый массив, применяя функцию к каждому элементу, filter возвращает новый массив с элементами, прошедшими проверку, а reduce применяет функцию к каждому элементу массива, аккумулируя результаты. Эти методы облегчают манипуляцию данными и делают код более читаемым и декларативным.

map(callback): Создает новый массив, в котором каждый элемент — это результат вызова функции callback для каждого элемента исходного массива. Например, array.map(x => x * 2) удваивает каждый элемент массива.

filter(callback): Создает новый массив с элементами, прошедшими проверку, определяемую функцией callback. Например, array.filter(x => x > 10) вернет все элементы больше 10.

reduce(callback, initialValue): Применяет функцию callback к каждому элементу массива, аккумулируя результат в одно значение. Например, array.reduce((sum, x) => sum + x, 0) суммирует все элементы массива.

forEach(callback): Выполняет указанную функцию callback для каждого элемента массива, но не возвращает новый массив. Например, array.forEach(x => console.log(x)) выводит каждый элемент в консоль.

push(element): Добавляет один или несколько элементов в конец массива и возвращает новую длину массива.

pop(): Удаляет последний элемент из массива и возвращает его.

shift(): Удаляет первый элемент из массива и возвращает его, изменяя длину массива.

unshift(element): Добавляет один или несколько элементов в начало массива и возвращает новую длину массива.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
11
Q

Что такое Object.keys, Object.values и Object.entries в JavaScript?

A

Object.keys(obj): Возвращает массив, содержащий все ключи (свойства) указанного объекта. Например, Object.keys({a: 1, b: 2}) вернет [‘a’, ‘b’].

Object.values(obj): Возвращает массив всех значений, соответствующих ключам объекта. Например, Object.values({a: 1, b: 2}) вернет [1, 2].

Object.entries(obj): Возвращает массив пар [ключ, значение] для каждого свойства объекта. Например, Object.entries({a: 1, b: 2}) вернет [[‘a’, 1], [‘b’, 2]]. Этот метод полезен для итерации по объектам с помощью методов массивов, таких как map или forEach.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
12
Q

Что такое деструктурирующее присваивание и как его использовать?

A

Деструктурирующее присваивание — это синтаксис в JavaScript, который позволяет распаковывать значения из массивов или свойства объектов в отдельные переменные.

Для массивов: можно извлечь значения из массива с помощью синтаксиса const [a, b] = array;. Например, если const arr = [1, 2, 3], то const [x, y] = arr; присвоит x = 1 и y = 2.

Для объектов: можно получить свойства объекта через const {name, age} = obj;. Если const obj = {name: ‘Alice’, age: 25}, то const {name, age} = obj; присвоит name = ‘Alice’ и age = 25.

Этот подход делает код более чистым и понятным, упрощая работу с данными и улучшая читаемость. Деструктуризация также может использоваться с параметрами функций, что позволяет более удобно передавать объект в функцию и извлекать необходимые значения.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
13
Q

Что такое остаточные параметры и оператор расширения в JavaScript?

A

Остаточные параметры (rest parameters) и оператор расширения (spread operator) — это две важные возможности в JavaScript, которые позволяют работать с массивами и функциями более гибко.

Остаточные параметры обозначаются троеточием (…) и позволяют функции принимать переменное количество аргументов. Они собирают оставшиеся аргументы в массив. Например:

function sum(…args) {
return args.reduce((total, num) => total + num, 0);
}
console.log(sum(1, 2, 3, 4)); // 10

Оператор расширения также используется с троеточием и позволяет развернуть массив или объект в отдельных элементах. Например:

const arr = [1, 2, 3];
const newArr = […arr, 4, 5]; // [1, 2, 3, 4, 5]

Эти возможности значительно упрощают работу с функциями и коллекциями, делая код более читаемым и кратким.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
14
Q

Что такое замыкание в JavaScript и как оно работает?

A

Замыкание — это функция, которая имеет доступ к своей собственной области видимости, области видимости внешней функции и глобальной области видимости, даже после завершения внешней функции. Замыкания позволяют создавать функции с «закрытыми» переменными, которые недоступны извне.

Пример:

function outerFunction() {
let outerVar = ‘Я внешний’;

function innerFunction() {
console.log(outerVar); // Доступ к внешней переменной
}

return innerFunction;
}

const myFunction = outerFunction();
myFunction(); // ‘Я внешний’

В этом примере innerFunction является замыканием, так как она имеет доступ к переменной outerVar, даже после завершения outerFunction. Замыкания полезны для создания приватных переменных и функций.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
15
Q

В чем разница между let, const и var в JavaScript?

A

let, const и var — это ключевые слова для объявления переменных в JavaScript, и между ними есть важные различия:

var: Используется для объявления переменных с функциональной или глобальной областью видимости. Подвержен всплытию (hoisting), что означает, что переменная доступна до ее объявления. Однако использование var не рекомендуется из-за его неожиданных особенностей.

let: Позволяет объявлять переменные с блочной областью видимости. Переменные, объявленные с помощью let, не доступны вне блока, в котором они были определены. В отличие от var, let не подвержен всплытию, если объявление находится в блоке.

const: Также имеет блочную область видимости, но используется для объявления констант, которые не могут быть переназначены. Однако это не делает сам объект неизменяемым — свойства объекта, объявленного с const, могут изменяться.

Пример:

var a = 1;
let b = 2;
const c = 3;

a = 4; // допустимо
b = 5; // допустимо
// c = 6; // ошибка: Assignment to constant variable

Рекомендуется использовать let и const для избежания проблем, связанных с областью видимости и переопределением переменных.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
16
Q

В чем разница между setTimeout и setInterval в JavaScript?

A

setTimeout и setInterval — это методы, используемые для планирования выполнения кода через заданные интервалы времени.

setTimeout(callback, delay): Выполняет функцию callback один раз после истечения указанного времени в миллисекундах (delay). Это полезно для задержки выполнения кода. Например:

setTimeout(() => {
console.log(‘Это сообщение появится через 2 секунды’);
}, 2000);
setInterval(callback, delay): Выполняет функцию callback регулярно, с заданным интервалом времени в миллисекундах. Это может быть полезно для повторяющихся задач, таких как обновление интерфейса или таймер. Например:

setInterval(() => {
console.log(‘Это сообщение будет появляться каждую секунду’);
}, 1000);

Важно помнить, что оба метода возвращают идентификатор таймера, который можно использовать для остановки выполнения с помощью clearTimeout или clearInterval.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
17
Q

Как работают методы call и apply в JavaScript?

A

call и apply — это методы функции, которые позволяют вызвать функцию с указанным значением this и передать аргументы.

call(thisArg, …args): Вызывает функцию с указанным значением this и принимает аргументы в виде отдельных значений. Например:

function greet() {
console.log(Привет, ${this.name});
}

const user = { name: ‘Алексей’ };
greet.call(user); // Привет, Алексей
apply(thisArg, [args]): Похож на call, но принимает аргументы в виде массива. Это удобно, когда количество аргументов заранее неизвестно. Например:

function sum(a, b) {
return a + b;
}

console.log(sum.apply(null, [1, 2])); // 3
Оба метода полезны для управления контекстом выполнения функции, особенно в ситуациях, когда необходимо использовать методы объектов или передавать контекст функции.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
18
Q

Что такое анонимные функции в JavaScript?

A

Анонимные функции — это функции, которые не имеют имени. Они могут быть определены и использованы в месте объявления, что позволяет создавать функции «на лету». Чаще всего анонимные функции используются как аргументы для других функций, таких как обработчики событий или в методах массивов. Пример:

setTimeout(function() {
console.log(‘Это анонимная функция’);
}, 1000);
Анонимные функции также могут быть стрелочными:

setTimeout(() => {
console.log(‘Это стрелочная анонимная функция’);
}, 1000);

Анонимные функции позволяют легко создавать временные функции, но могут затруднить отладку, так как они не имеют имен.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
19
Q

Что такое всплытие (hoisting) в JavaScript?

A

Всплытие — это механизм в JavaScript, при котором объявления переменных и функций перемещаются в верхнюю часть их области видимости во время компиляции. Это означает, что вы можете использовать переменные и функции до их фактического объявления в коде.

Пример с функцией:

console.log(myFunction()); // “Привет”
function myFunction() {
return “Привет”;
}

Пример с переменной:

console.log(a); // undefined
var a = 5;
console.log(a); // 5
В случае с переменной, её значение будет undefined до фактического присваивания, но объявление переменной будет «всплывать». Важно помнить, что let и const не подвержены всплытию, так как они имеют блочную область видимости и вызов до их объявления приведет к ошибке.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
20
Q

В чем разница между объявлением функции (function declaration) и выражением функции (function expression)?

A

Объявление функции и выражение функции — это два способа создания функций в JavaScript, и между ними есть ключевые различия.

Объявление функции (function declaration): Это более традиционный способ создания функций. Функции, объявленные таким образом, доступны в любом месте своей области видимости благодаря всплытию. Например:

function myFunction() {
console.log(‘Привет’);
}
Выражение функции (function expression): Функции, созданные с помощью выражений, могут быть анонимными или именованными, и они не подвержены всплытию. Такие функции доступны только после их объявления. Например:

const myFunction = function() {
console.log(‘Привет’);
};

Таким образом, при использовании выражений функции они должны быть объявлены перед использованием, в то время как объявления функций могут быть вызваны до их фактического определения.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
21
Q

В чем ключевые различия между старым JavaScript и новым (ES6 и выше)?

A

С появлением ES6 и последующих версий JavaScript, язык претерпел значительные изменения и улучшения. Вот некоторые ключевые различия:

Синтаксис: Новый синтаксис включает стрелочные функции, шаблонные литералы (template literals), деструктуризацию и короткие записи для объектов, что делает код более лаконичным и читаемым.

Объявление переменных: Появление let и const позволяет избежать проблем с областью видимости и всплытием, которые были присущи var.

Классы: ES6 ввел синтаксис классов для создания объектов, что делает OOP более интуитивно понятным.

class Animal {
constructor(name) {
this.name = name;
}
}
Модули: Новый JavaScript поддерживает модули, позволяя организовать код и импортировать/экспортировать функциональность между файлами.

Промисы: Вместо коллбеков для обработки асинхронных операций введены промисы, что улучшает управление асинхронным кодом.

Эти изменения сделали JavaScript более мощным, гибким и удобным для разработчиков.

How well did you know this?
1
Not at all
2
3
4
5
Perfectly
22
Q

В чем основные отличия стрелочных функций от обычных функций?

A

Стрелочные функции, введенные в ES6, имеют несколько ключевых отличий от обычных функций:

Синтаксис: Стрелочные функции имеют более компактный синтаксис, что делает код более лаконичным. Например:

const add = (a, b) => a + b;
Контекст this: Одним из самых значительных отличий является то, что стрелочные функции не имеют собственного контекста this. Они наследуют его из окружающего контекста, что делает их особенно полезными при работе с методами объектов и коллбеками, избегая необходимости использовать bind.

Отсутствие arguments: Стрелочные функции не имеют объекта arguments, что может ограничивать их использование в некоторых случаях, где требуется доступ к аргументам функции.

Невозможность использования в качестве конструкторов: Стрелочные функции не могут быть использованы с оператором new, в отличие от обычных функций, что делает их более подходящими для создания коротких функций или коллбеков.

Эти отличия делают стрелочные функции мощным инструментом, особенно при работе с современными библиотеками и фреймворками.

23
Q

Что такое виртуальный дом (Virtual DOM) и зачем он нужен?

A

Виртуальный дом — это концепция, используемая в библиотеках и фреймворках, таких как React, для оптимизации манипуляций с реальным DOM. Он представляет собой легковесное представление реального DOM, которое хранится в памяти. Когда состояние приложения изменяется, вместо непосредственного обновления реального DOM, обновляется виртуальный дом. Затем происходит сравнение между предыдущим и текущим состоянием виртуального дома с использованием алгоритма диффов.

После этого изменения применяются только к реальному DOM, минимизируя количество операций и улучшая производительность. Это особенно важно для сложных интерфейсов, где частые изменения состояния могут значительно замедлить работу приложения, если каждое изменение требует обновления реального DOM.

24
Q

Почему разработчики отказываются от jQuery, что не так с домом, и как React отличается от него?

A

Разработчики все чаще отказываются от jQuery в пользу современных фреймворков, таких как React, по нескольким причинам. Во-первых, jQuery в значительной степени основан на манипуляциях с реальным DOM, что может привести к плохой производительности в сложных приложениях. React же использует виртуальный DOM для оптимизации обновлений интерфейса, минимизируя ненужные операции.

Во-вторых, jQuery не предоставляет четкой структуры для разработки, что может привести к сложностям в масштабировании приложений. React, напротив, использует компонентный подход, позволяя разработчикам создавать переиспользуемые компоненты, что упрощает организацию и сопровождение кода.

Кроме того, современный JavaScript (ES6+) включает функции, такие как fetch и Promise, которые делают многие возможности jQuery избыточными. React предлагает более современный подход к разработке пользовательских интерфейсов, включая управление состоянием и использование хуков.

25
Q

Если писать на хуках, какой классовый компонент для этого нужен?

A

Если вы используете хуки в React, вам не нужен классовый компонент, так как хуки позволяют управлять состоянием и жизненным циклом компонента без необходимости использовать классы. Однако, если вы хотите создать функциональный компонент, который использует хуки, вам все равно может понадобиться класс, если вы используете функционал, который доступен только в классовых компонентах, например, Error Boundaries.

Классовые компоненты все еще могут быть полезны, но с появлением хуков и функциональных компонентов многие разработчики предпочитают писать компоненты без классов, так как это делает код более лаконичным и читабельным. В общем, использование хуков позволяет избежать дополнительных сложностей, связанных с классами, такими как привязка методов.

26
Q

Что такое компоненты жизненного цикла в React?

A

Компоненты жизненного цикла в React — это методы, которые позволяют отслеживать состояние компонента на различных этапах его существования. Жизненный цикл компонента делится на три основных фазы:

Монтирование: Это когда компонент создается и добавляется в DOM. Методы жизненного цикла, такие как componentDidMount, позволяют выполнять действия сразу после монтирования компонента, например, загрузку данных.

Обновление: Это когда состояние или пропсы компонента изменяются. Методы, такие как componentDidUpdate, могут использоваться для выполнения действий после обновления компонента.

Размонтирование: Это когда компонент удаляется из DOM. Метод componentWillUnmount позволяет выполнять очистку, например, отмену таймеров или подписок.

С введением хуков в React 16.8, функциональные компоненты могут использовать хуки, такие как useEffect, для выполнения аналогичных действий без необходимости использовать классы.

27
Q

Что такое контекст в React?

A

Контекст в React — это механизм, который позволяет передавать данные через дерево компонентов без необходимости передавать их явно через пропсы на каждом уровне. Он особенно полезен для глобальных данных, таких как текущая аутентификация пользователя, настройки темы или язык интерфейса.

Контекст создается с помощью React.createContext, который возвращает два компонента: Provider и Consumer. Provider используется для определения значения контекста и оборачивания компонентов, которые должны получить доступ к этому значению. Consumer позволяет компонентам подписываться на изменения контекста.

С введением хуков, React предлагает useContext, который упрощает получение значений из контекста без использования Consumer, что делает код более лаконичным.

28
Q

Что такое Redux, зачем он нужен, из чего состоит и почему не MobX?

A

Redux — это библиотека для управления состоянием приложений на JavaScript, особенно часто используемая с React. Она помогает организовать и централизовать состояние приложения, что упрощает его управление и отладку.

Основные компоненты Redux включают:

Store: Централизованное хранилище, где хранится всё состояние приложения.
Actions: Простые объекты, которые описывают, что произошло. Они могут содержать полезную информацию для обновления состояния.
Reducers: Функции, которые принимают текущее состояние и действие, и возвращают новое состояние. Они определяют, как состояние приложения изменяется в ответ на действия.
Redux отличается от MobX тем, что использует подход, основанный на предсказуемости состояния, что упрощает отладку и тестирование. MobX, с другой стороны, основан на реактивном программировании и предлагает более гибкий подход к управлению состоянием, но может быть сложнее в крупных приложениях из-за его динамического характера. Выбор между Redux и MobX зависит от специфики проекта и предпочтений команды разработчиков.

29
Q

Как осуществляется авторизация в веб-приложениях и какие существуют способы?

A

Авторизация в веб-приложениях — это процесс проверки, имеет ли пользователь право доступа к определенным ресурсам или действиям. Существует несколько способов реализации авторизации:

Форма входа (Login Form): Пользователь вводит свои учетные данные (логин и пароль), которые проверяются на сервере. Если учетные данные верны, сервер создает сессию и отправляет пользователю токен (например, JWT — JSON Web Token), который будет использоваться для дальнейших запросов.

OAuth: Протокол авторизации, который позволяет пользователям входить в приложение, используя учетные записи других сервисов (например, Google, Facebook). Это упрощает процесс входа и повышает безопасность, так как не нужно передавать пароль.

Multi-Factor Authentication (MFA): Дополнительный уровень безопасности, который требует от пользователя предоставить два или более доказательства своей личности. Например, после ввода пароля пользователь может получить SMS с кодом для подтверждения.

Single Sign-On (SSO): Позволяет пользователю входить в несколько приложений с одной учетной записью, что упрощает управление учетными записями и повышает удобство использования.

Каждый из этих методов имеет свои преимущества и недостатки, и выбор зависит от требований к безопасности и удобству использования приложения.

30
Q

Что такое препроцессоры для стилей и зачем они нужны?

A

Препроцессоры для стилей — это инструменты, которые расширяют возможности CSS, добавляя такие функции, как переменные, вложенные правила, миксины и функции. Они позволяют разработчикам писать более структурированный и удобочитаемый код, который затем компилируется в стандартный CSS.

Наиболее популярные препроцессоры:

Sass (Syntactically Awesome Style Sheets): Позволяет использовать вложенные правила, переменные и функции. Sass поддерживает два синтаксиса: SCSS (более похожий на CSS) и indented syntax (использует отступы вместо фигурных скобок).

LESS: Предлагает аналогичные функции, такие как переменные, миксины и вложенные правила, и имеет более простой синтаксис по сравнению с Sass.

Stylus: Очень гибкий и минималистичный препроцессор, который позволяет писать код в разных стилях, включая возможность использования отступов.

Препроцессоры помогают улучшить организацию стилей и сделать код более переиспользуемым, что упрощает поддержку и масштабирование проектов.

31
Q

Что такое специфичность селекторов в CSS?

A

Специфичность селекторов — это система, которая определяет, какой стиль применяется к элементам, если несколько селекторов соответствуют одному и тому же элементу. Специфичность рассчитывается на основе типа селектора:

Inline-стили (например, style=”…”) имеют наивысшую специфичность и всегда применяются.
ID-селекторы (например, #id) имеют более высокую специфичность, чем классовые и атрибутные селекторы.
Классы, атрибутные и псевдоклассы (например, .class, [type=”text”], :hover) имеют одинаковую специфичность, но ниже, чем у ID.
Теговые селекторы (например, div, p) имеют наименьшую специфичность.
При конфликте стилей браузер применяет правило с самой высокой специфичностью. Если специфичность одинакова, то применяется последнее правило в коде. Понимание специфичности помогает разработчикам избежать неожиданных конфликтов стилей и упрощает отладку CSS.

32
Q

Что такое event loop в JavaScript?

A

Event loop (цикл событий) — это механизм, который позволяет JavaScript выполнять асинхронные операции, не блокируя основной поток выполнения. JavaScript является однопоточной языковой, что означает, что он выполняет код последовательно, одну операцию за раз.

Event loop работает следующим образом:

Когда вызывается асинхронная функция (например, setTimeout, fetch), она отправляется в Web API, а основной поток продолжает выполнение следующего кода.
После завершения асинхронной операции, результат помещается в очередь событий (callback queue).
Event loop проверяет, свободен ли стек вызовов (call stack). Если стек пуст, он берет функции из очереди событий и помещает их в стек для выполнения.
Этот механизм позволяет JavaScript эффективно обрабатывать множество операций, таких как клики мышью, запросы к серверу и таймеры, не блокируя выполнение основного кода.

33
Q

Что такое debounce и как он работает?

A

Debounce — это техника оптимизации, используемая для ограничения частоты вызова функции. Она особенно полезна в сценариях, когда необходимо обработать события, которые могут происходить очень часто, такие как ввод текста или прокрутка страницы.

Работа дебаунса основана на установке таймера, который откладывает выполнение функции до тех пор, пока не пройдет определенный интервал времени с последнего вызова. Если функция вызывается снова до истечения этого времени, таймер сбрасывается. Это означает, что функция будет вызвана только после того, как пользователь прекратит активные действия.

Например, при вводе текста в поле поиска функция для фильтрации результатов может быть обернута в дебаунс, чтобы избежать слишком частого вызова API, что может привести к перегрузке сервера.

34
Q

В чем отличие типов any и unknown в TypeScript?

A

В TypeScript any и unknown — это два типа, которые позволяют работать с переменными, чьи типы неизвестны. Однако они имеют разные уровни безопасности.

any: Это тип, который отключает проверку типов. Использование any позволяет работать с любыми значениями, но лишает вас всех преимуществ типизации, так как компилятор не будет проверять корректность операций с переменной типа any.

unknown: Это более безопасный тип, который также может принимать любые значения, но требует проверки типа перед использованием. Если переменная имеет тип unknown, перед тем как вы сможете использовать её, необходимо явно проверить её тип, что повышает безопасность кода и предотвращает потенциальные ошибки.

Таким образом, использование unknown предпочтительнее в тех случаях, когда вы хотите сохранить безопасность типов и избежать ошибок, связанных с неявными преобразованиями.

35
Q

В чем разница между виртуальным DOM и реальным DOM?

A

Реальный DOM (Document Object Model) — это представление структуры документа HTML, которое браузер использует для отображения страницы. Каждое изменение в реальном DOM требует перерисовки части или всей страницы, что может быть медленным процессом, особенно при частых обновлениях.

Виртуальный DOM — это легковесное представление реального DOM, используемое библиотеками, такими как React. Когда происходит изменение состояния компонента, React обновляет виртуальный DOM вместо реального. Затем React сравнивает изменения в виртуальном DOM с предыдущим состоянием (с помощью алгоритма «диффинга») и определяет минимальный набор изменений, которые необходимо применить к реальному DOM. Этот подход значительно ускоряет обновления интерфейса, улучшая производительность приложения и снижая нагрузку на браузер.

36
Q

В чем разница между управляемыми и неуправляемыми инпутами в React?

A

Управляемые инпуты — это компоненты формы, чье значение управляется состоянием React. Значение инпута хранится в state, и изменение этого значения происходит через обработчики событий, что позволяет контролировать и валидировать ввод данных в реальном времени. Например:

function ControlledInput() {
const [value, setValue] = useState(‘’);

return (
<input
type=”text”
value={value}
onChange={e => setValue(e.target.value)}
/>
);
}
Неуправляемые инпуты не управляются React, и их значение хранится непосредственно в DOM. Это упрощает код, так как не требуется обработка состояния в React, но ограничивает возможности управления и валидации данных. Пример:

function UncontrolledInput() {
const inputRef = useRef(null);

const handleSubmit = () => {
alert(inputRef.current.value);
};

return (
<>
<input ref={inputRef} type=”text” />
<button onClick={handleSubmit}>Submit</button>
</>
);
}

37
Q

Что такое Redux и как он работает?

A

Redux — это библиотека для управления состоянием приложения, разработанная для JavaScript. Она основана на принципах единого источника правды, неизменяемости и строгих правилах управления состоянием. Основные концепции Redux:

Store: Хранилище состояния приложения. В нем хранится всё состояние приложения в виде одного объекта.

Actions: Описание изменений состояния. Это обычные объекты, содержащие тип действия и дополнительные данные (payload), необходимые для изменения состояния.

Reducers: Функции, которые принимают текущее состояние и действие, а затем возвращают новое состояние. Reducers — это чистые функции, которые не изменяют входные данные.

Dispatch: Метод, используемый для отправки действий в Redux Store. При вызове dispatch вызывается соответствующий reducer, который обновляет состояние.

Redux предоставляет дополнительные инструменты, такие как middleware (например, redux-thunk), которые позволяют обрабатывать асинхронные действия и побочные эффекты. Это делает Redux мощным инструментом для управления состоянием в больших и сложных приложениях.

38
Q

Как в JavaScript работают объекты и ссылки, и что такое глубокое копирование?

A

В JavaScript объекты и массивы являются ссылочными типами данных. Это означает, что при присваивании объекта другой переменной не создается его копия, а обе переменные ссылаются на один и тот же объект в памяти. Например:

javascript
Копировать код
const obj1 = { name: ‘Alice’ };
const obj2 = obj1; // obj2 ссылается на тот же объект, что и obj1
obj2.name = ‘Bob’; // Изменение obj2 также изменяет obj1
console.log(obj1.name); // ‘Bob’
Глубокое копирование — это процесс создания копии объекта, при котором все вложенные объекты также копируются. Это позволяет изменять копию, не затрагивая оригинал. В JavaScript глубокое копирование можно реализовать с помощью функций, таких как JSON.parse(JSON.stringify(object)), но этот метод имеет ограничения (например, он не копирует функции и специальные объекты, такие как Date).

Для более сложных объектов можно использовать библиотеки, такие как Lodash, которые предоставляют функции для глубокого копирования объектов.

39
Q

Что такое прототипы и прототипная цепочка в JavaScript?

A

Прототипы — это механизм, используемый в JavaScript для реализации наследования и повторного использования кода. Каждый объект в JavaScript имеет свойство [[Prototype]] (или __proto__), которое ссылается на другой объект. Этот объект называется прототипом.

Прототипная цепочка (prototype chain) — это цепочка объектов, которая позволяет JavaScript искать свойства и методы. Когда вы обращаетесь к свойству объекта, JavaScript сначала проверяет наличие этого свойства у самого объекта. Если его нет, он ищет в его прототипе и продолжает подниматься по цепочке прототипов, пока не найдет свойство или не достигнет конца цепочки (обычно это null).

Этот механизм позволяет создавать объекты, которые наследуют свойства и методы от других объектов, что делает код более гибким и переиспользуемым. Например:

function Animal(name) {
this.name = name;
}

Animal.prototype.speak = function() {
console.log(${this.name} делает звук.);
};

const dog = new Animal(‘Собака’);
dog.speak(); // ‘Собака делает звук.’

40
Q

Что такое всплытие и погружение событий в JavaScript?

A

Всплытие и погружение — это два механизма обработки событий в JavaScript.

Всплытие (Event Bubbling): Процесс, при котором событие начинается от целевого элемента и “всплывает” вверх по дереву DOM к родительским элементам. Например, если пользователь кликает на кнопку, событие клика сначала обрабатывается на самой кнопке, а затем на ее родительских элементах.

Погружение (Event Capturing): Обратный процесс, при котором событие сначала обрабатывается на верхнем уровне (родительском элементе) и “погружается” вниз к целевому элементу. Это менее распространено, чем всплытие, и обычно используется реже.

В JavaScript события по умолчанию обрабатываются с использованием всплытия, но можно явно указать режим обработки события при добавлении слушателя, используя параметр true для захвата:

element.addEventListener(‘click’, handler, true); // Включает захват

41
Q

Что такое батчинг в контексте JavaScript и React?

A

Батчинг (batching) — это процесс группирования нескольких обновлений состояния или изменений в одно, чтобы оптимизировать производительность. В JavaScript это позволяет выполнять несколько операций, минимизируя количество обновлений DOM или вызовов функций.

В контексте React батчинг используется для объединения нескольких обновлений состояния, происходящих в рамках одного события (например, обработчика клика). Это снижает количество перерисовок компонентов и улучшает производительность приложения. Например, если вы вызываете несколько функций setState в одном обработчике, React объединяет эти вызовы и обновляет компонент единовременно, что снижает нагрузку на рендеринг:

const handleClick = () => {
setState1(value1);
setState2(value2);
// Обновления будут обработаны вместе
};
В более ранних версиях React батчинг работал только в обработчиках событий, но в новых версиях React поддерживает автоматический батчинг асинхронных вызовов, что дополнительно улучшает производительность.

42
Q

Что такое куки и как работает Document.cookie в JavaScript?

A

Куки (cookies) — это небольшие текстовые файлы, которые хранятся на стороне клиента и используются для сохранения информации о пользователе, сессиях или предпочтениях. Куки часто применяются для аутентификации, отслеживания сессий и хранения пользовательских настроек.

В JavaScript доступ к кукам осуществляется через объект document.cookie. Куки можно создавать, читать и удалять с помощью этой переменной. Формат записи куков:

document.cookie = “username=John; expires=Fri, 31 Dec 2024 23:59:59 GMT; path=/”;
В этом примере создается кука с именем username, значением John, сроком действия до 31 декабря 2024 года и доступом для всех страниц сайта (path=/).

43
Q

В чем разница между событиями DOMContentLoaded, load, beforeunload и unload?

A

Эти события относятся к жизненному циклу загрузки веб-страницы и позволяют управлять действиями на различных этапах:

DOMContentLoaded: Это событие срабатывает, когда весь HTML документ был полностью загружен и разобран, без ожидания загрузки стилей, изображений и подкадров. Оно полезно для инициализации JavaScript, когда DOM уже доступен, но еще не все ресурсы загружены.

load: Это событие происходит, когда все ресурсы страницы (включая изображения, стили и скрипты) были полностью загружены. Оно полезно для выполнения кода, который зависит от всех ресурсов, находящихся на странице.

beforeunload: Это событие срабатывает перед тем, как пользователь покинет страницу (например, закрывает вкладку или переходит на другой URL). Это событие можно использовать для предупреждения пользователей о несохраненных изменениях.

unload: Это событие происходит, когда пользователь покидает страницу. В отличие от beforeunload, unload не позволяет отменить уход со страницы и не поддерживает синхронные операции, такие как отправка данных на сервер.

44
Q

В чем разница между LocalStorage и sessionStorage?

A

LocalStorage и sessionStorage — это два типа веб-репозитория, доступные через API Web Storage, которые позволяют сохранять данные в браузере.

LocalStorage: Данные хранятся в браузере без срока действия, даже если пользователь закрывает вкладку или браузер. Данные доступны на всех страницах одного домена. Это удобно для хранения информации, которая должна быть доступна при следующих визитах пользователя на сайт.

sessionStorage: Данные хранятся только на время текущей сессии. Как только вкладка или окно браузера закрываются, данные удаляются. Это подходит для хранения временной информации, такой как данные форм или состояние приложения в рамках одной сессии.

Оба типа хранилищ позволяют сохранять строки, но только LocalStorage поддерживает более длинные данные и общую область видимости для всех вкладок.

45
Q

Что такое браузерные события и как они работают?

A

Браузерные события — это уведомления, которые браузер отправляет JavaScript-коду при возникновении определенных действий или изменений в пользовательском интерфейсе. Это могут быть действия пользователя (такие как клики, нажатия клавиш, перемещение мыши) или системные события (такие как загрузка страницы или изменение размера окна).

Каждое событие может быть обработано с помощью слушателей событий, которые регистрируются с помощью метода addEventListener. Слушатели могут реагировать на события, выполняя определенные функции. Например:

document.getElementById(‘myButton’).addEventListener(‘click’, () => {
alert(‘Кнопка нажата!’);
});
Браузерные события позволяют разработчикам создавать интерактивные веб-приложения и улучшать пользовательский опыт.

46
Q

Что такое делегирование событий и как его использовать?

A

Делегирование событий — это техника, которая позволяет обрабатывать события на родительском элементе, а не на каждом дочернем элементе отдельно. Это особенно полезно, когда количество дочерних элементов изменяется динамически (например, при добавлении или удалении элементов).

Преимущество делегирования заключается в том, что вместо регистрации слушателей событий на каждом элементе, вы можете зарегистрировать один слушатель на родительском элементе. Например:

document.getElementById(‘parent’).addEventListener(‘click’, (event) => {
if (event.target.matches(‘.child’)) {
alert(‘Дочерний элемент нажат!’);
}
});
Таким образом, если вы добавите новых дочерних элементов с классом child, они автоматически будут обрабатывать событие клика без необходимости добавления новых слушателей.

47
Q

Что такое действия браузера по умолчанию и как их предотвратить?

A

Действия браузера по умолчанию — это стандартные реакции браузера на определенные события. Например, при нажатии на ссылку браузер переходит по указанному URL, а при отправке формы — обновляет страницу.

Чтобы предотвратить выполнение этих действий, можно использовать метод preventDefault() объекта события. Это полезно, когда вы хотите реализовать собственное поведение, например, валидацию данных перед отправкой формы:

document.querySelector(‘form’).addEventListener(‘submit’, (event) => {
event.preventDefault(); // Отменяет стандартное поведение отправки формы
// Ваша логика валидации и отправки
});
Таким образом, вы можете контролировать, как ваш веб-приложение реагирует на взаимодействие пользователя.

48
Q

Разница между Null и Undefined?

A

null и undefined в JavaScript — это два разных типа, которые используются для обозначения отсутствия значений, но у них разные значения и цели:

undefined: Переменная имеет значение undefined, если она была объявлена, но не инициализирована значением. Также undefined возвращается, если функция не вернула результат, а также когда обращаемся к несуществующему свойству объекта:

javascript
let a;
console.log(a); // undefined
null: Значение null означает “отсутствие значения”, но его нужно присваивать вручную, чтобы явно указать, что переменная не содержит данных. Например, null указывает на “пустое” или “неопределенное” состояние, часто используется в случаях, когда значение должно отсутствовать намеренно:

javascript
let b = null;
console.log(b); // null
В итоге, undefined означает, что значение еще не было установлено, а null указывает на умышленное отсутствие значения.

49
Q

Что такое шаблонные литералы и зачем они нужны?

A

Шаблонные литералы (template literals) — это способ создания строк в JavaScript, который использует обратные кавычки (`) вместо обычных одинарных или двойных кавычек. Они позволяют легко создавать строки с подстановкой значений, многострочные строки, а также поддерживают выражения внутри строк.

Шаблонные литералы нужны, чтобы:

Упрощать вставку переменных и выражений в строку с помощью синтаксиса ${expression}, без необходимости использовать конкатенацию +:

javascript
const name = “Alice”;
const greeting = Hello, ${name}!;
console.log(greeting); // “Hello, Alice!”
Создавать многострочные строки без символов переноса \n или конкатенации, что делает код более читабельным:

javascript
const text = This is a multi-line string.;
console.log(text);
Выполнять выражения прямо в строке, что позволяет вставлять результат вычислений:

javascript
const a = 5;
const b = 10;
console.log(Sum is ${a + b}); // “Sum is 15”
Шаблонные литералы делают код чище, особенно при работе со строками, которые требуют подстановки значений и многострочного формата.

50
Q

Что такое Set и Map?

A

В JavaScript, Set и Map — это встроенные структуры данных, используемые для хранения уникальных значений и пар ключ-значение.

Set:

Это коллекция уникальных значений (дубликаты автоматически удаляются).
Может хранить любые типы значений (строки, числа, объекты и т.д.).
В отличие от массивов, у Set нет индексов для доступа к элементам.
Поддерживает методы, такие как .add(value), .delete(value), .has(value), и .clear().
Пример использования Set:

javascript
const set = new Set();
set.add(1);
set.add(2);
set.add(2); // Дубликат, не будет добавлен.
console.log(set); // Set { 1, 2 }
Map:

Это коллекция для хранения пар ключ-значение.
В отличие от объектов, ключи могут быть не только строками, но и любыми типами данных (например, объектами или функциями).
Поддерживает методы, такие как .set(key, value), .get(key), .delete(key), и .has(key).
Пример использования Map:

javascript
const map = new Map();
map.set(‘name’, ‘Alice’);
map.set(123, ‘NumberKey’);
console.log(map.get(‘name’)); // Alice
console.log(map); // Map { ‘name’ => ‘Alice’, 123 => ‘NumberKey’ }
Когда использовать:

Используйте Set, если вам нужна коллекция уникальных значений без определенного порядка.
Используйте Map, если нужно ассоциировать значения с уникальными ключами, особенно если ключи могут быть не строками.

51
Q

Как определить наличие свойства в объекте?

A

Чтобы определить наличие свойства в объекте в JavaScript, можно использовать несколько подходов:

Оператор in: Проверяет, есть ли указанное свойство в объекте или его прототипе.

javascript
Копировать код
const obj = { name: “Alice” };
console.log(“name” in obj); // true
console.log(“age” in obj); // false
Метод hasOwnProperty: Проверяет только свойства объекта, игнорируя свойства, унаследованные от прототипов.

javascript
Копировать код
const obj = { name: “Alice” };
console.log(obj.hasOwnProperty(“name”)); // true
console.log(obj.hasOwnProperty(“age”)); // false
Сравнение с undefined: Если значение свойства известно, но есть риск, что оно может быть undefined, можно использовать строгое сравнение.

javascript
Копировать код
const obj = { name: “Alice”, age: undefined };
console.log(obj.age !== undefined); // false, свойство есть, но значение undefined
console.log(obj.name !== undefined); // true
Выбор метода зависит от того, нужно ли проверять только “собственные” свойства объекта или учитывать унаследованные свойства.

52
Q

Какие способы создания объекта вы знаете?

A

Литеральная нотация: Создание объекта напрямую с помощью фигурных скобок {}. Это наиболее простой и часто используемый метод.

javascript
const obj = { name: “Alice”, age: 25 };
Функция-конструктор: Используется для создания множества экземпляров объектов с одинаковой структурой. Новые свойства добавляются с помощью this.

javascript
function Person(name, age) {
this.name = name;
this.age = age;
}
const person1 = new Person(“Alice”, 25);
Классы (ES6): Классы представляют собой более современный и удобный способ создания объектов, введённый в ES6. Это своего рода синтаксический сахар над функцией-конструктором, который упрощает создание и наследование объектов.

javascript
class Person {
constructor(name, age) {
this.name = name;
this.age = age;
}
}
const person2 = new Person(“Bob”, 30);
Эти способы позволяют создавать объекты разной сложности в зависимости от задач и требований.

53
Q

какие значения будут являться falsy значениями?

A

В JavaScript следующие значения считаются “falsy” — то есть приводятся к false в логическом контексте: (!! - приведение к логическому типу)

false
0 (и -0)
“” (пустая строка)
null
undefined
NaN

54
Q

Что такое promise?

A

Promise — это объект в JavaScript, представляющий результат асинхронной операции, которая может завершиться успешным результатом или ошибкой. Промисы упрощают работу с асинхронными действиями, такими как загрузка данных или выполнение таймеров, помогая избежать вложенных коллбеков (так называемой «адской пирамиды»).

Структура и состояние промиса:
Промис может находиться в одном из трех состояний:

Pending (ожидание): начальное состояние, когда промис ещё не завершён.
Fulfilled (выполнен): операция завершена успешно, и промис возвращает результат.
Rejected (отклонён): произошла ошибка, и промис возвращает причину отклонения.
Создание и использование промисов:

javascript
const promise = new Promise((resolve, reject) => {
// Асинхронная операция
setTimeout(() => {
const success = true;
if (success) {
resolve(“Операция успешна!”); // Промис выполнен
} else {
reject(“Произошла ошибка.”); // Промис отклонён
}
}, 1000);
});

promise
.then(result => console.log(result)) // Выполнится при успешном завершении
.catch(error => console.log(error)) // Выполнится в случае ошибки
.finally(() => console.log(“Завершено”)); // Выполняется в любом случае
Зачем нужны промисы?
Промисы удобны для обработки асинхронных операций в цепочке, улучшая читаемость кода и управление последовательностью выполнения, а также способствуют лучшей обработке ошибок.

55
Q

Что такое async, await для ассинхронных запросов?

A

async и await — это синтаксические возможности в JavaScript для работы с асинхронным кодом, которые делают его более понятным и удобным.

async — это ключевое слово, которое используется для объявления функции асинхронной. Функция, помеченная как async, автоматически возвращает промис, и внутри нее можно использовать await.

await — это оператор, который используется внутри асинхронной функции и позволяет ожидать завершения промиса. Он приостанавливает выполнение кода до тех пор, пока промис не завершится (либо успешно, либо с ошибкой).

Пример:
javascript
// Асинхронная функция
async function fetchData() {
try {
let response = await fetch(‘https://jsonplaceholder.typicode.com/posts’);
let data = await response.json();
console.log(data); // данные успешно получены
} catch (error) {
console.error(‘Ошибка:’, error); // обработка ошибки
}
}

fetchData();
fetchData — это асинхронная функция.
Внутри нее используется await, чтобы дождаться завершения fetch (передает результат запроса в переменную response).
Если произошла ошибка, она будет поймана в блоке catch.
Основные преимущества:
С помощью async/await код становится линейным и читаемым, в отличие от цепочек промисов.
await позволяет работать с асинхронными операциями как с синхронными, делая их менее сложными для понимания.

56
Q
A