Templates e Conceitos¶
Templates definem famílias de tipos ou funções. A instanciação substitui argumentos e verifica o programa. Conceitos nomeiam restrições e melhoram interfaces e diagnósticos.
Template de função¶
Isso exige < utilizável e retorno compatível, mas a assinatura não comunica a exigência.
Template restrito¶
#include <concepts>
template<std::totally_ordered T>
T maximum(T left, T right) {
return left < right ? right : left;
}
Conceito é predicado em compilação. Especifica sintaxe e, por documentação, expectativas comportamentais. O compilador não prova leis como transitividade.
Conceito personalizado¶
template<typename R>
concept SizedRange = requires(R const& range) {
{ range.size() } -> std::convertible_to<std::size_t>;
range.begin();
range.end();
};
Restrinja no nível realmente necessário; exigir contêiner concreto reduz reutilização.
Instanciação e visibilidade¶
Definições precisam estar visíveis na instanciação implícita, por isso ficam em headers. Instanciação explícita pode mover gerações selecionadas. Toda especialização obedece à ODR.
Templates de classe e dedução¶
template<typename T>
class box {
public:
explicit box(T value) : value_{std::move(value)} {}
T const& get() const noexcept { return value_; }
private:
T value_;
};
box value{std::string{"notes"}}; // class template argument deduction
Polimorfismo estático e type erasure¶
Templates permitem inlining concreto. Type erasure, como std::function, oferece
interface uniforme em runtime. Interfaces virtuais, variants, templates e
apagamento diferem em extensibilidade, alocação, ABI, compilação e diagnósticos.
Exercícios¶
- Restrinja função de média a intervalo numérico e resultado válido.
- Explique propriedades semânticas que um conceito não prova.
- Compare estratégia virtual e por template.