Задать вопрос
  • Как реализовать частичную специализацию для указателя на определённый класс?

    @MarkusD Куратор тега C++
    А, еще забыл сказать что так же хорошо подойдет подход аналогично std::char_traits.
    en.cppreference.com/w/cpp/string/char_traits
    Это шаблон класса, созданный непосредственно для частного инстанцирования и определения набора статических функций, которыми пользуется основной шаблон (для тебя это будет класс List).
  • Как реализовать частичную специализацию для указателя на определённый класс?

    @MarkusD Куратор тега C++
    CodeInside , неа, не понял. :)
    К сожалению я даже общий замысел уловить не смог. Но кое-что другое между собой связать удалось.

    Обратись за помощью к подходам traits / toolkit. Конкретно для твоей ситуации видно что нужны именно черты - traits. Для тебя это будет шаблонная функция, которую уже можно специфицировать.
    Примерно так:
    namespace NodeListTraits
    {
    	template< typename TNodeType, typename TDataype >
    	void AddHead( TDataype data, TNodeType node )
    	{
    		// Общая реализация.
    	};
    
    	template< typename TNodeType >
    	void AddHead( Storage_device* data, TNodeType node )
    	{
    		// Спецификация для `Storage_device`.
    	};
    };
    
    template< typename TNodeType, typename TDataype >
    void List<TNodeType, TDataype>::AddHead( TDataype data )
    {
    	// ...
    	
    	// Черты лучше вызывать только через ADL.
    	NodeListTraits::AddHead( data, node );
    }


    После этого черты можно расширять как душе угодно. Главное - это чтобы для конкретного модуля трансляции специализация черты была описана выше ее использования. Удобнее всего специализировать черты непосредственно рядом с описанием типа, для которого черта специализируется.В твоем случае - это рядом с описанием типа Storage_device.
    Еще надо помнить про ADL (Argument Dependent Lookup) и что черты на самом деле - это семейство перегруженных шаблонов и чистых функций. Поэтому никаких явных раскрытий шаблона функции при ее вызове.
  • Как реализовать частичную специализацию для указателя на определённый класс?

    @MarkusD Куратор тега C++
    CodeInside , методы шаблонного класса не могут быть специализированы без частного инстанцирования или частичной специализации самого шаблона. Поэтому ответ Антон Жилин является единственным решением.
    Еще мы можем побеседовать о причине желания специализировать метод. Может у меня найдется выход для твоей ситуации.
  • Использование вариативного шаблона функции без аргументов?

    @MarkusD Куратор тега C++
    Nexeon , поэтому всю работу по отслеживанию занятых битов и все обеспечение удобства работы перекладывают на компилятор. Ни один человек в здравом уме не начнет следить за обеспечением уникальности номеров битов для компонентов. :)

    Чтобы уловить это все, тебе стоит почитать о том, как делался Autodesk Stingray.
    bitsquid.blogspot.ru/2014/09/building-data-oriente...
    Там 4 или 5 статей в блоге, далее по датам после вот этой.

    Суть такова: компоненты для ECS сперва регистрируются. Это нужно не только для их индексации, но и для оптимизации хранения компонентов, и для оптимального управления компонентами для сущности.
  • Использование вариативного шаблона функции без аргументов?

    @MarkusD Куратор тега C++
    Nexeon , да, правильно. :)
    Смотри, в EntityX, Autodesk Stingray, Artemis и у меня в моем фреймворке применяются маски и индексирование компонентов.

    Коротко: на этапе компиляции (ага, снова метапрограммирование) для каждого типа компонента рассчитывается битовый индекс - это всего один поднятый бит на участке из N бит (int32_t, int64_t, 128, 256..). В EntityX, к примеру, это номер бита для std::bitset. Я предпочитаю снова все делать на этапе компиляции.
    У каждой сущности есть битовое поле - маска компонентов. Когда компонент добавляется, в маске поднимается его бит, при удалении - снимается.
    При этом, проверка наличия компонента делается через проверку соответствующего компоненту бита. А для проверки группы компонентов делается битовая маска группы, проверка все так же делается через одну операцию.

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

    Это уже потребует некоторой библиотеки метапрограммирования - MPL. Без нее сделать это все становится сложнее.
  • Использование вариативного шаблона функции без аргументов?

    @MarkusD Куратор тега C++
    Nexeon , весь этот код уже можно отнести к разделу метапрограммирования в C++... Да, я все время забываю что это необычная тема.
    Не прямо такой, а подобный код я имею обыкновение создавать и использовать в своей работе. Он работает. :)

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

    std::all_of - простая замена цикла по итерируемому множеству с аккумулятором через операцию `&&`.
    В качестве множества для std::all_of хорошо подходит массив указателей на функции проверки одного одиночного компонента.
    В результате компилятор пишет код проверки группы компонентов за нас. :)

    И еще вот наглядная демонстрация работы этого метода.
    cpp.sh/8b5xo

    Folding expressions безусловно удобнее... Все жду начала широкой поддержки 17го стандарта всеми популярными компиляторами...
  • Что происходит с переменной / указателем в памяти после его обнуления?

    @MarkusD Куратор тега C++
    Nexeon , уупс... А я даже не заметил что это твой вопрос. Да и на дату не посмотрел. Кажется, мне положена золотая лопата. ))
  • Почему компилятор не видит метод класса?

    @MarkusD Куратор тега C++
    nkorobkov , все зависит от того, чем ты пользуешься для сборки своего проекта.
  • Ошибка use of undeclared identifier, как побороть?

    @MarkusD Куратор тега C++
    Airat1995 , тогда сразу меняй эти старые ненужные define-guard-ы на #pragma once.
    И не забудь пожалуйста отметить ответ fshp как решение. Чтобы люди не агрились на вопрос. :)
  • Использование вариативного шаблона функции без аргументов?

    @MarkusD Куратор тега C++
    Nexeon , я специально засунул лямбду в all_of, чтобы создать простор для модификаций.
    На деле у тебя ведь `HasComponent` является member function? В этом случае тип предиката будет таким:
    using CheckingPred = bool (Entity::*)();

    В лямбде нужно замыкание на this от Entity, ну и вызов предикатов из листа будет немного другим:
    auto my_entity = this;
    return std::all_of(
    	predicates.begin(), predicates.end(),
    	[my_entity]( CheckingPred stored_pred ) -> bool
    	{
    		return (my_entity->*stored_pred)();
    	}
    );
  • Использование вариативного шаблона функции без аргументов?

    @MarkusD Куратор тега C++
    MiiNiPaa , со всеми бывает. :)
    Я на самом деле тоже не сразу ее увидел, у меня пальцы просто сами не смогли назвать вариативный шаблон `HasComponent`. ))
  • Использование вариативного шаблона функции без аргументов?

    @MarkusD Куратор тега C++
    MiiNiPaa , о_О??
    Nexeon попросил вариативную `bool HasComponents()`, а не `bool HasComponent()`. :)
  • Как избавиться от привычки усложнять задачу?

    Александр Синицын , фантазия - штука очень хорошая и безоговорочно полезная. :)
    Однако. Увлекаться нельзя. Понимаешь, я сам маялся этим делом с самого начала карьеры. А с ростом проф. уровня мои загоны становились только круче. Строго оговоренный MVP в этом случае решает.
    romy4 , пожалуй ближе всего к ответу, т.к. правильно все описал.

    Итого, с привычкой усложнять боремся через самоограничение. Работаем не дальше оговоренных рамок задачи. Чувство границы - это тот момент, когда тебе хочется хоть что-то продумать наперед (за пределами MVP) без железно отработанного опыта.
  • Почему компилятор не видит метод класса?

    @MarkusD Куратор тега C++
    nkorobkov , не, из-за чего-то другого, парень просто так тебе написал это. :)

    Система сборки проекта у тебя какая? У тебя многофайловый проект, тебе надо задать сценарии сборки всех файлов исходного кода и линковки их всех в бинарный файл.
  • Где слабое место игрового компьютера с такой конфигурацией для GTA V?

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

    Ну и... AMD. Как бы хорошо я не относился к этой фирме (и видеокарты у них лучше, и SoC для мобильников производительнее), но игры сейчас оптимизируются под запуск на процессорах Intel (это фигня, но от этого пока не уйти).
  • Почему теряем данные типа string в с++?

    @MarkusD Куратор тега C++
    Андрей , в этом случае лучше самостоятельно ответить на свой вопрос и пометить ответ как решение. Не стоит саботировать правила тостера.

    Детально ответ лучше оформить так, чтобы всем было понятно где ты ошибся. Что-то вроде такого:
    В своем списке ты хранил объекты типа Person по значению, при добавлении в список объекта типа Adult происходило копирование только данных Person. После этого приведение типа Person к типу Adult становилось бессмысленным, а вызов функции `GetDescription()` приводил к выходу за границы памяти объекта и вызывал ошибку доступа к памяти.

    Кстати, это выдает незнание/непонимание самых базовых моментов работы с языком. Поэтому Джеффа Элджера тебе в помощь.
  • Как построить наименьшую траекторию перемещения по клеткам, имея возможность переставлять препятствия?

    muzclubs , да не, не надо.
    Сложность задачи от разнообразия препятствий не меняется. К тому, же, даже если все препятствия могут двигаться на любую из 8 клеток вокруг себя, то если два препятствия стоят вплотную рядом, у них уже появляется специфика перемещения. Они уже не могут перемещаться на клетки друг друга. И так далее.
    Случай с шахматными фигурами никак не усложняет поиск, ведь цель передвижения препятствий - освободить оптимальный путь перемещения.

    Может нам лучше перевести обсуждение непосредственно в область задачи? А то я так и чую что ты стараешься обойтись только наводящими вопросами. :)
  • Как построить наименьшую траекторию перемещения по клеткам, имея возможность переставлять препятствия?

    muzclubs , таких игр море - это жанр "push the box" или "sokoban". :) Только, да, в жанре предусмотрено непосредственное взаимодействие игрока с коробкой.
    Можно подумать, наверное, так.
    Можно построить взвешенный граф оптимального перемещения. В этом графе должны быть не только свободные клетки, но и все препятствия на пути оптимального перемещения. По этому графу станет видно, нужно ли вообще двигать препятствия. Пусть изначально переход на место препятствия будет вдвое дороже перехода на свободную клетку.
    А далее начинается "оптимизация" графа. Армянское Радио правильную мыслю подсказывает.
    Оптимизация заключается в том, чтобы попробовать отодвинуть самые "дешевые" препятствия, всякий раз пересчитывая стоимость всего пути.

    Еще можно упростить себе жизнь, задав потенциальное поле удорожания маршрута на клетке каждого препятствия. В этом случае первым этапом будет создание потенциального поля. Оно создается от наиболее близких к свободным клеткам препятствий к центру их массы и буквально определяет удорожание пути при движении сквозь препятствия. А вторым шагом будет простой A*.
  • Почему теряем данные типа string в с++?

    @MarkusD Куратор тега C++
    Андрей , давай я взамен предложу тебе отгадать, почему следующий код работает? :)
    ideone.com/6R0fKH