JavaScript: Неизменяемость
Что напечатает на экран последний вызов?
const name = 'Tirion';
console.log(name.toUpperCase()); // => TIRION
console.log(name); // => ?Ответ на этот вопрос зависит от того, как вы поняли урок про неизменяемость примитивных типов данных. Вызов метода .toUpperCase() возвращает новое значение, в котором все буквы преобразованы в верхний регистр, но он не меняет (и не может этого сделать) исходную строку. Поэтому внутри константы (или переменной — это не важно) окажется старое значение: 'Tirion'. Эта логика справедлива для методов всех примитивных типов.
Методы не меняют оригинал
Когда мы вызываем метод у строки, кажется, что мы меняем её. На самом деле метод возвращает новую строку, а оригинал остаётся прежним:
const text = 'hexlet';
text.toUpperCase();
console.log(text); // => hexletЧтобы не потерять результат, его нужно сохранить в переменную:
const text = 'hexlet';
const upperText = text.toUpperCase();
console.log(upperText); // => HEXLETЕсли не сохранить результат метода, он просто потеряется. Другие методы работают так же. Например, trim() возвращает новую строку без пробелов по краям, а исходная остаётся прежней:
const text = ' hi ';
const cleaned = text.trim();
console.log(cleaned); // => 'hi', без пробелов
console.log(text); // => ' hi ', строка не измениласьБолее того, попытка изменить значение свойства тоже ни к чему не приведёт:
const name = 'Tirion';
console.log(name.length); // => 6
name.length = 100;
console.log(name.length); // => 6Так сделано специально: примитивные значения нельзя изменить после создания. Случайно испортить строку невозможно, а движок может переиспользовать одинаковые строки в памяти, экономя ресурсы.
Переприсвоение переменной
Вместо изменения значения его можно заменить. Для этого понадобится переменная (let):
let name = 'Tirion';
name = name.toUpperCase();
console.log(name); // => TIRIONЗаписывать результат обратно в ту же переменную уместно, когда суть данных не меняется. После trim() это тот же текст, просто чище. Но если результат метода представляет другую сущность, лучше дать ей отдельное имя:
const fullName = 'John Doe';
const headerName = fullName.toUpperCase();fullName — имя человека, headerName — его вариант для заголовка. Это разные вещи, и хранить их в одной переменной было бы путаницей. Имя переменной должно отражать смысл данных, которые в ней лежат.
Задание
Данные, вводимые пользователями, часто содержат лишние пробельные символы в конце или начале строки. Обычно их вырезают с помощью метода .trim(), например, было: ' hello\n ', стало: 'hello'.
Обновите переменную firstName записав в неё то же самое значение, но обработанное методом .trim(). Распечатайте то, что получилось, на экран.
Полезное
Ваше упражнение проверяется по этим тестам
// @ts-check
import { expect, test, vi } from 'vitest';
test('methods immutability', async () => {
const consoleLogSpy = vi.spyOn(console, 'log');
await import('./index.js');
const firstArg = consoleLogSpy.mock.calls.join('\n');
expect(firstArg).toBe('Grigor');
});Решение учителя откроется через:
20:00
