Как стать автором
Обновить

Комментарии 40

Каждому времени свои this-испытания :D

this is javascript baby))

this-пытания, прастити

Лучше название self

Дай угадаю: знаток Ruby? 😁

или делфист

Может перекликаться с window.self.

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

ПС Я пишу бэк, но было пару пет проектов на js / ts.

Да, это действительно банальное перекрытие области видимости, но для новичков даже оно иногда выглядит как магия. А что для вас казалось необъяснимым чудом в коде?

Смею предположить, что каждого своя боль и магия на старте)))))

Боже, какое банальное перекрытие области видимости? Причем тут вообще область видимости?

При чем тут перекрытие?

function f1(id: string) {
  const f2 = (id: number) => {}
}

Вот перекрытие.

Потому что в js нет неявного обращения к this, если я правильно вас понял.

Так же как и в c++, когда в конструкторе класса указываешь age = _age, а перед этим int age; вне конструктора,

да и зачем в функции использовать this, когда уже давно используются классы?
class Person {
contructor(age, name) {
this.name = name;
this.age = age;
}
}

но можно пойти дальше!

constructor(obj) {
for (const key of Object.keys(obj))
this[key] = obj[key];
}

и тогда new Person({
name: 'test',
age: 5
});

будет сразу получать свойства без лишних this[var] = value;

Согласна, решение с передачей объекта в конструктор выглядит гораздо элегантнее и убирает всю эту рутину с this[var] = value. Прямо минимализм, который и читать приятнее, и писать быстрее.

Подход с передачей объекта в конструктор и автоматическим присваиванием свойств выглядит лаконично. Часто ли используете его на практике? Есть ли подводные камни?

Я у себя использую вот такое:

export default class Fl64_Gpt_User_Back_Mod_Auth {
    constructor(
        {
            Fl64_Gpt_User_Back_Defaults$: DEF,
            TeqFw_Core_Back_Config$: config,
            TeqFw_Core_Shared_Api_Logger$$: logger,
            Fl64_Gpt_User_Back_Mod_User$: modUser,
            Fl64_Gpt_User_Back_Mod_Token$: modToken,
            'Fl64_Gpt_User_Shared_Enum_User_Status.default': STATUS,
        }
    ) {
        this.isValidRequest = async function (req) {...};
        this.loadUser = async function ({trx, pin, passPhrase}) {...};
    }
}

Все зависимости используются "по месту", прямо из конструктора. Ничего переприсваивать не надо. Периодически находятся индивиды, которые говорят, что так делать некошерно. Ну, у меня в приложении объекты, как правило, синглтоны, да и стиль близок к функциональщине - мне норм. Но для обычного ООП такое, конечно, диковато.

за именование - медаль.

Вы конечно можете смеяться, но... с такими именами очень удобно программировать с LLM :) Они сразу втыкают, о чём речь (в отличие от "кожанных мешков"). К тому же это просто калька с java'вского package и с PHP'шного namespace , адаптированная под текущие реалии JS. Примерно такой же подход использовался в PHP <5.3. Ищите "PHP Zend 1 namespaces".

Я использую разные решения, то что написал - лишь один из способов, но если свойств меньше 3-5, то мне проще this.var = var писать,

Вообще можно даже не циклом, а просто сделать у класса свойство params и в него добавлять объект со свойствами и потом их вызывать obj.params.var, вроде как тоже имеет место быть

Вот еще в интернете нашел интересный способ:
class Person { name; age; constructor(properties) { Object.assign(this, properties); } }

for (const key of Object.keys(obj))

this[key] = obj[key];

}

Object.assign(this, obj);

Давно не писал на javascript, на C# решаем проблему соглашениями по именованию. Т е чтобы не писать this.name = name пишем, например, _name = name или Name = name. Вообще, для меня использование this - плохой тон, почти всегда (вообще всегда, кроме пары синтетических примеров) можно обойтись без него. В C# конечно.

Не понимаю. Вроде же понятно все и явно, идет присваивание параметров, атрибутам класса. На Java давно так пишу и вижу, что другие пишут. По мне так так лучше, чем именовать атрибуты класса mName = name или еще круче mName = pName. С this человек со стороны, не зная местных правил именований сразу разберется, что к чему. А вот что значит "_name = name" , вот тут как раз я бы подвис. Опять же нет необходимости выдумывать разные имена для параметров и атрибутов класса. Чем однообразнее, согласованее названия, тем кмк проще потом разбирать код, искать в нем.

Да все понятно и очень явно :) Тут, конечно, дело вкуса, а о вкусах не спорят. Я не предлагаю называть филды mName или pName - все это точно такой же camelCase. Всё же, мои соображения таковы:

  1. Параметры метода - camelCase. Как и локальные переменные (обычно). У нас не какой-то супер-кастомный code style, +- все так делают (это пусть будет аксиома)

  2. Вот смотришь на ревью, добавлена строчка name = 1 . Будем считать, что присваивать значения input параметрам метода - плохая практика. Это локальная переменная, или человек забыл написать this? А если есть и локальная переменная с таким именем, и филд - как понять? А если написано _name = 1 - всё сразу ясно и понятно.

  3. В принципе и так всегда должно быть понятно, что ты хочешь сделать. Код, который не требует комментариев, все дела. Если необходимо уточнять свои намерения, добавляя this - код уже ну типа не очень ясный. Если это не нужно - то и this не нужен.

  4. Отдельный смак - это проперти. Будем считать, что проперти пишутся в PascalCase (в C# +- все так делают, не знаю, есть ли проперти в Java). Писать this.Name = 1 - чтобы что? Неужели где-то в глобальной области видимости есть Name который можно присвоить?

  5. А вызовы методов? this.Method() - как и в прошлом пункте, шанс того, что тут можно что-то перепутать, крайне невелик.

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

Насчет человека со стороны. У нас люди не так часто меняются, но все же, когда это происходит - есть .editorconfig, stylecop и набор анализаторов, так что проблем с тем, чтобы вникнуть, не возникает. Даже без этого, если человек на основе одного-двух файлов не может понять, что к чему - может лучше с ним и не работать вообще.

А вот так написать религия не позволяет?

class Person {
  constructor (
    public name,
    public age,
    public anyProperty
  ) {}
}

Только это уже тайпскрипт

это не typescript, а javascript

Это именно typescript, потому что в js нет сахарного синтаксиса parameter properties, превращающего аргументы конструктора в свойства класса при использовании модификаторов public, private, protected и readonly. Собственно, интерпретатор js выдаст ошибку о некорректном синтаксисе.

спасибо, поспешил. не знал

Наверное, проблема была в том, что знак = читался как "равно". А нужно было читать как "присваивается значение".

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

А моя личная боль на первых порах была в том, что никак не мог въехать в "возвращаемое значение". Хорошо помню как это раздражало в очередном тьюториале - "кто возвращает", "куда" и главное "зачем". Сейчас конечно смешно, но тогда это выглядело не то, что "магия", а какой-то мировой заговор преподавателей, которые твердят одно и то же, но не хотят объяснить толком что это такое.

У меня так с "регистром" в процессорах было - что значит "именованная ячейка памяти", зачем её именовать и почему просто не дать цифровой адрес, как всем остальным ячейкам памяти? Пока сам не стал использовать (не понимая!) в программах, так и морщил мозг, что это за фигня такая. С тех пор даже не напрягаюсь, если использую что-то, не понимая, как оно там внури всё устроено. Придёт время - пойму, а не пойму - значит и не надо было.

Я помню вначале пути путался с рекурсиями. Тогда для меня они выглядели, как магия.

Или может было что-то иное?

Меня ментально напрягли массивы в js, особенно массивы с "дырками". Странные на фоне массивов в других языках, где они являются непрерывным куском памяти. Сейчас отношусь к ним философски, но долгое время было не совсем понятно, с чем имею дело)

Не использую this в JS, чувствую себя отлично.

Это автор ещё C# не видел, где в последнее время принято this вообще не писать, из-за чего можно вполне увидеть подобные строчки:

Name = name;

Name: name,

Связано это с тем, что у C# довольно чёткие требования к кодстайлу и стиль наименования переменных, полей и свойств говорит о их области видимости.

Но если честно это по своему удобно.

Если честно, вообще не понимаю чьей либо боли относительно this... Пишешь код без использования this. Если в библиотеке - читаешь документацию. Если в современном js - есть классы и там всегда this = инстанс класса. Стрелочная функция = this родительской функции либо его отсутствие... И на худой конец ты сам можешь задать this через условный байнд - на моей практике потребовалось лишь пару раз....

Согласен. Видимо многим сложно разобраться на что указывает this. Отсюда гора шедевриальных советов, как не использовать this. Например, отказаться от классов.

может было что-то иное?

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

Зарегистрируйтесь на Хабре, чтобы оставить комментарий

Публикации

Истории