Как в зависимости от типа переменной выполнить определённые действия?

Изучаю шаблоны в С++, работаю с шаблоном класса - нужно реализовать дек (векторная реализация), при этом по выбору пользователя работа идёт либо с элементами типа char, либо типа int.
Проблема возникла при написании метода извлечения элемента с конца дека - функция возвращает значение, извлечённое с конца дека, типа char или int. В случае, если дек пуст, необходимо возвращать что-то другое. Можно бы было зарезервировать одно значение, обозначающее, что дек пуст (например, возвращать INT_MIN), но это значение будет другим для типа char.
Как в зависимости от типа вернуть нужное значение (задача сводится к вопросу "как определить тип переменной")? Хотелось бы решение без использования sizeof, чтобы этот вопрос решить и для других типов на будущее. Буду также рад другим вариантам, если определения типа можно избежать.


Ответы (4 шт):

Автор решения: Anton Shchyrov

Значение возвращать по ссылке, а пусто/не пусто как результат функции false/true

→ Ссылка
Автор решения: dIm0n

Тип выражения можно определить с помощью decltype.

Сравнить тип с другим можно с помощью std::is_same_v.

Возвращать либо int, либо char можно с помощью std::variant.

Пример:

#include <iostream>
#include <type_traits>

template <class T>
void foo() {
    std::cout << std::is_same_v<T, int> << ' '
              << std::is_same_v<T, char> << '\n';
}

int main() {
    foo<int>();
    foo<char>();
    foo<double>();
}

Доки:

https://en.cppreference.com/w/cpp/language/decltype

https://en.cppreference.com/w/cpp/types/is_same

https://en.cppreference.com/w/cpp/utility/variant

→ Ссылка
Автор решения: Harry

Например, так:

template<typename T>
T value()
{
    if constexpr (is_same_v<T,int>) return -10000;
    else if constexpr (is_same_v<T,char>) return 'a';
    else return T{};
}

int main()
{
    cout << value<int>()    << endl;
    cout << value<char>()   << endl;
    cout << value<double>() << endl;
}

Но ваша идея с возвратом того, чего нет - плоха...

→ Ссылка
Автор решения: Ildar

как насчет явной специализации шаблона, определяете поведение метода под конкретный параметр шаблона

#include <iostream>

template <typename T>
class Dummy
{
public:
  void foo();
};

template <>
void Dummy<int>::foo()
{
  std::cout << "int\n";
}

template <>
void Dummy<char>::foo()
{
  std::cout << "char\n";
}


int main()
{
  Dummy<int> d1;
  Dummy<char> d2;

  d1.foo(); // int
  d2.foo(); // char

  return 0;
}
→ Ссылка