• Как отменить несколько коммитов в форкнутом репозитории?

    sergey-kuznetsov
    @sergey-kuznetsov Куратор тега Git
    Автоматизатор
    Репозиторий уже содержит ВСЕ версии проекта. Не совсем понятно что именно вам нужно.
    Если хочется актуальный main откатить на 5 коммитов назад, то клонируйте форк к себе на компьютер, затем откатите нужную ветку назад через git reset --hard HEAD~5 и отправьте обратно git push --force
    Ответ написан
    Комментировать
  • Как отменить несколько коммитов в форкнутом репозитории?

    bingo347
    @bingo347
    Crazy on performance...
    git checkout <хэш нужного коммита>
    git checkout -b <имя новой ветки>

    И продолжаем разработку в этой ветке.
    Или если просто собрать приложение, то можно и без новой ветки
    Ответ написан
    Комментировать
  • Можно ли очищать setTimeout внутри setTimeout?

    dollar
    @dollar
    Делай добро и бросай его в воду.
    Можно.

    Только для setTimeout() это не имеет смысла, ибо он одноразовый.
    Это имеет смысл для setInterval()
    Ответ написан
    3 комментария
  • Как вызывать функцию с теми же аргументами не более одного раза?

    sergiks
    @sergiks Куратор тега JavaScript
    ♬♬
    memoization
    это называется «мемоизация» (не от слова «мем», нет : ) Функция запоминает значения аргументов и результат выполнения. Если уже вызывалась с такими аргументами – вернёт «запомненное» значение, не выполняясь ещё раз. Статья на Хабре

    В качестве кэша можно использовать объект или WeakMap, если аргумент – объект.

    distributed lock
    Из вопроса не вполне понятно: в контексте одного выполнения скрипта только один раз, или глобально? Для глобального случая можно использовать какое-то быстрое хранилище, например, Redis, и механизм MutEx ("mutual exclusion" – взаимного исключения), например RedLock.

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

    Генерится случайный ключ. Пара (X, ключ) отправляется в асинхронное хранилище, где если нет ещё сохранённого значения под этот X, ячейка запирается (lock) этим ключом. Тут необходима особенность механизма самого хранилища – в Redis это "NX" – записывать только, если уже нет значения. Это гарантирует, при параллельных запросах, что только чьё-то одно случайное значение запишется. Закон джунглей: первый прибежал — наелся!

    Далее надо прочитать записанное значение и получить ключ. Сравнить со своим ранее сгенеренным ключом. Совпали? Значит, это именно мы заперли этот аргумент, и можно выполнить функцию. Не совпали – параллельный процесс выиграл. Просто запросим готовое значение чуть попозже.
    Ответ написан
    1 комментарий
  • Являются ли стрелочные функции аналогом bind функций?

    iiiBird
    @iiiBird
    Пока ты спишь - твой конкурент совершенствуется
    2 комментария
  • Как сделать асинхронный метод объекта в классе, который проверяет загрузку картинки и только потом срабатвает функция drawImage?

    RAX7
    @RAX7
    Сделай вспомогательную функцию для загрузки картинок, которая будет возвращать промис. Код с созданием персонажа оберни в асинхронную функцию и дождись в ней загрузки картинки.
    const canvas = document.getElementById('canvas');
    
    function loadImage(src) {
      return new Promise((resolve, reject) => {
        const image = new Image();
        image.src = src;
    
        if (image.complete) {
          resolve(image);
          return;
        }
    
        image.onload = () => resolve(image);
        image.onerror = (e) => reject(e);
      });
    }
    
    class Character {
      constructor(options) {
        this.ctx = options.ctx;
    
        this.image = options.image;
        this.width = options.width;
        this.height = options.height;
    
        this.render();
      }
    
      load() {}
    
      render() {
        this.ctx.drawImage(this.image, 0, 0, this.width / 7, this.height, 0, 0, this.width / 7, this.height);
      }
    }
    
    (async function main() {
      const spriteImage = await loadImage('./img/sprite.png');
    
      const character = new Character({
        ctx: canvas.getContext('2d'),
        image: spriteImage,
        width: 448,
        height: 60,
      });
    })();
    Ответ написан
    Комментировать
  • Visual Studio Code как создать структуру html?

    RAX7
    @RAX7
    За эту фичу отвечает расширение emmet которое идет в комплекте с vscodом.
    нажимая ! + ентер

    Может все же ! + tab.
    Проверь включена ли настройка "emmet.triggerExpansionOnTab": true
    62c860d52c2d9440252051.png
    Ответ написан
    1 комментарий
  • Как проверить передан ли в параметр функции event?

    RAX7
    @RAX7
    Можно с помощью оператора instanceof
    function func(data) {
      if (data instanceof Event) {
        var id = data.target.id;
      } else {
        var id = data;
      }
    }

    Но лучше использовать кастомные события и проверять наличие поля detail в объекте события
    function func(event) {
      const id = event.detail ? event.detail.id : event.target.id;
    }
    domElement.dispatchEvent(new CustomEvent('event-name', { detail: { id: 'id-42' } }));
    Ответ написан
    1 комментарий
  • Как проверить передан ли в параметр функции event?

    sergiks
    @sergiks Куратор тега JavaScript
    ♬♬
    Попробовать так и сяк
    function func(mixedData) {
      const id = mixedData?.target?.id ?? mixedData;
      console.log(id);
    }
    
    func(123) // 123
    func({target: {id: 456}}) // 456

    Что это было?!
    ?.optional chaining
    ??Nullish coalescing operator

    Но это всё не фэн-шуёво, не аккуратненько как-то.
    Лучше бы функции строго принимать один тип параметра — ожидать только id.
    А что-то поменять при вызовах.
    Ответ написан
    6 комментариев
  • Зачем нужна инкапсуляция в ООП?

    Adamos
    @Adamos
    Инкапсуляция действительно защищает - мозг программиста от переполнения. И только.
    Машинный код после компиляции класса, в котором методы и члены объявлены private или public - один и тот же.
    Они нужны только для автоматической проверки компилятором - не ошибся ли программист.
    А инкапсуляция - это не столько собирание в одну кучу того, что работает вместе, сколько обрывание любых связей с остальным кодом. За исключением реально необходимых. После чего класс становится вещью в себе, и вам можно работать с ним, не задумываясь о прочем коде, и работать с прочим кодом, не думая о потрохах этого класса.
    Ответ написан
    4 комментария
  • Зачем нужна инкапсуляция в ООП?

    delphinpro
    @delphinpro
    frontend developer
    Инкапсуляция - это грубо говоря объединение связанного функционала. В ООП в виде класса.
    Плюс скрытие деталей реализации функциональности.

    Если говорить о ваших классах Database и URL, то в первом объединяются функции работы с базой, а во втором с адресами. Это первое.
    Второе: Классы имеют публичный интерфейс. Работая с классом через этот интерфейс, вам не нужно знать что происходит внутри. Достаточно знать, что дать на вход, и что вы получите на выходе.
    Ответ написан
    2 комментария
  • Зачем нужна инкапсуляция в ООП?

    Starina_js
    @Starina_js
    full-stack web dev
    Да, есть такая проблема, путаница в понятиях, плюс разные языки программирования по своему трактуют и реализуют такой механизм.

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

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

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

    Пример: бизнес торопиться вывести новую функцию на рынок. Чем быстрее выведет, тем быстрее начнет зарабатывать. Бизнес просит программистов делать это побыстрее. Программисты пыхтят, у них высокая нагрузка им некогда разбираться с чужим кодом. Видят нужное им свойство, начинают с ним работать и изменяют под себя.
    Вроде все ок, и программа не упала и все тесты прошли, начали релизить проект. Прошла неделя и пользователь как-то нестандартно использовал новую функциональность и вместо 100 руб, списался 1 миллион. Беда косяк, а бывают и серьезней последствия. Случилось это потому, что кто-то изменил маленькое свойство в чужом коде.

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

    Кстати инкапсуляция это не только "про" или даже "в" ООП, оно вполне себе реализуется и в функциональном программировании.

    Как-то так)
    Ответ написан
    Комментировать
  • Зачем нужна инкапсуляция в ООП?

    AlexNest
    @AlexNest
    Работаю с Python/Django
    Да начнется холивар
    Видел кучу разных, зачастую противоположных, мнений, но на мой взгляд - инкапсуляция не равно сокрытие (про которое вы и пишите, судя по типам полей).
    Сокрытие является частным случаем инкапсуляции. В общем же случае инкапсуляция подразумевает объединение связанных элементов в один объект. Например есть юзер. У него есть разные свойства (логин-пароль/аватарка/id-шка). И если данные можно хранить в структурах (словари/массивы/списки и т.д,), то функции, описывающие взаимодействие с этим юзером просто так не сгруппируешь. Для этого и придумали инкапсуляцию и ООП.
    Сокрытие же в этом случае может применяться например для создания "точки входа" при работе с паролем для защиты от "дураков"/предварительной обработки/проверки данных.
    Делаем поле private и все, "тупо изменить" его извне уже нельзя. Для его изменения мы предоставляем метод, который перед тем как изменить его (условно):
    • Валидирует значения по заданным критериям
    • Проверяет наличие прав на изменение пароля

    UPD.
    но кто сможет потом их поменять, если я не добавлю функцию для изменения?

    Ну, видимо никто. Если не добавите советующую функцию.
    Какая разница, private я установил или public, функции для изменения не будет у программы и никто и никак не сможет поменять этот URL.

    Ну, в этом смысла нет, но можно упомянуть какие-то внутренние вещи. Например сессии юзера. Извне методы работы с ними в таком классе не доступны в принципе, для безопасности. Но внутри класса к ним есть доступ у других медодов.
    Ответ написан
    5 комментариев
  • Зачем нужна инкапсуляция в ООП?

    firedragon
    @firedragon
    Не джун-мидл-сеньор, а трус-балбес-бывалый.
    Зайдите в гараж. В одном углу сварочник и электроды , в другом верстак, там сверлилка и коробки со свёрлами, дальше коробка с метизами. Все упорядочено и не нужно далеко ходить. Это будет инкапсуляция. В другом все свалено вместе и метизы и свёрла и отвертки и ножовки. Прежде чем начать работу вы ищете инструменты и детали
    Ответ написан
    2 комментария
  • Как проверить, что хотя бы одно значение во вложенных объектах равно false?

    0xD34F
    @0xD34F Куратор тега Vue.js
    isValid() {
      return Object.values(obj).flatMap(Object.values).every(n => n.valid);
    },

    Или даже так, чтобы лишний раз values-flatMap не дёргать при изменениях значений свойств valid:

    objects() {
      return Object.values(this.obj).flatMap(Object.values);
    },
    isValid() {
      return this.objects.every(n => n.valid);
    },
    Ответ написан
    Комментировать
  • Какую книгу прочитать по JavaScript со средним уровнем знания js?

    black1277
    @black1277
    Вольный стрелок
    Прочитайте серию книг "Вы пока еще не знаете JS" Кайла Симпсона, есть издания 2022г.
    Ответ написан
    Комментировать
  • Как правильно типизировать функцию?

    bingo347
    @bingo347 Куратор тега TypeScript
    Crazy on performance...
    function preparedData<T extends Record<string, {name: string, id: string}[]>>(data: T) {
      return Object.keys(data).map((key) => {
        return data[key as keyof T].map((a) => ({
          val: a.name,
          newId: a.id,
        }));
      });
    }

    https://www.typescriptlang.org/play?#code/GYVwdgxg...
    Ответ написан
    Комментировать
  • Как остановить проверку?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега JavaScript
    Ваш код очень бажный. Во-первых, вы не проверяете результат выполнения indexOf и проверка работает ровно наоборот. Во-вторых, значение поискового поля вы добавляете не в виде get-параметра, а прямо в тело адреса, что снова делает предыдущую проверку нерабочей. Ну и наконец, даже если всё это исправить, у вас всё равно будет баг - любой get-параметр, название которого заканчивается на "q", будет попадать под условие и подстановка не произойдёт.

    Максимально тупое решение в лоб с перезагрузкой страницы:
    if (
        window.location.search.indexOf('?q=') === -1 &&
        window.location.search.indexOf('&q=') === -1
    ) {
        window.location.search += (window.location.search ? '&' : '?' ) + 'q=' + searchInput.value;
    }


    В современном же js есть куда более удобные инструменты для решения этой задачи:
    https://developer.mozilla.org/en-US/docs/Web/API/U...
    https://developer.mozilla.org/ru/docs/Web/API/Hist...
    Ответ написан
    Комментировать
  • Что означает "разделить макет по таскам"?

    Вероятно, имеются в виду блоки, на которые можно разделить страницу и отдать их на вёрстку разным людям в виде отдельных самодостаточных задач (тасков).
    Но конкретно так обычно не говорят, так что ваше замешательство вполне оправдано.
    Ответ написан
    6 комментариев
  • Как называть картинки в реальном проекте? 01-02 или полное название?

    delphinpro
    @delphinpro Куратор тега Вёрстка
    frontend developer
    В верстке удобнее называть порядковыми именами с группировкой в папках.
    При этом подобные изображения лучше поместить в отдельную директорию, чтобы впоследствии программист четко понимал, какие картинки ему нафиг не нужны, потому что они будут добавляться через админку, и их можно смело удалить.
    Например

    /images
      /content
        /gallery
          /1.jpg
          /2.jpg
          /3.jpg
        /slider
          /1.jpg
          /2.jpg
          /3.jpg


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

    <div class="slider">
      {% for i in 1..3 %}
        <div class="slide">
          <img src="/images/content/slider/{{ i }}.jpg">
        </div>
      {% endfor %}
    </div>


    А как там будут называть файлы в боевом проекте контент-менеджеры - уже не ваша забота.
    Ответ написан
    Комментировать