テンプレートクラス内のusingによるエイリアス宣言について
背景
以下のようなテンプレートクラスにおいて、
使用する型を短縮したい場合がある。
例えばコンテナ型を用いる場合、テンプレートが入れ子になって
ごちゃごちゃして見づらい。
template <class T, class K> class ScoreTable { public: // 型名が長すぎる using Dmap = std::unordered_map<T, std::unordered_map<K, int>>; int GetScore(T row, K col); void SetScore(T row, K col, int val); void SetDmap(Dmap &dmap); private: std::unordered_map<T, std::unordered_map<K, int>>dmap_; };
これをこうしたい。
// どこかで以下を宣言 using Dmap = std::unordered_map<T, std::unordered_map<K, int>>; // 型がすっきりに template <class T, class K> class ScoreTable { public: int GetScore(T row, K col); void SetScore(T row, K col, int val); void SetDmap(Dmap &dmap); private: Dmap dmap_; };
問題点
テンプレートクラスで使うためにはグローバル空間で
using宣言はできない?と考えclass内でusing宣言にする作戦。
ただ、void SedDmap()関数は引数に Dmap型を使うため、
外部にDmap型を知らせるのかわからなかった。
結論
classのpublicに型エイリアスを宣言する。
エイリアスをクラスから参照できることを知らなかった。
適当にクラス内で宣言して使っていたが、
privateになっていることが頭から抜けていた。
ソースコード
double_map.h
#ifndef DOUBLE_MAP_H_ #define DOUBLE_MAP_H_ #include <unordered_map> template <class T, class K> class ScoreTable { public: using Dmap = std::unordered_map<T, std::unordered_map<K, int>>; int GetScore(T row, K col); void SetScore(T row, K col, int val); void SetDmap(Dmap &dmap); private: Dmap dmap_; }; template <class T, class K> int ScoreTable<T, K>::GetScore(T row, K col) { return dmap_.at(row).at(col); } template <class T, class K> void ScoreTable<T, K>::SetScore(T row, K col, int val) { dmap_.insert({row, {}}); dmap_[row].insert({col, val}); } template <class T, class K> void ScoreTable<T, K>::SetDmap(Dmap &dmap) { dmap_ = std::move(dmap); } #endif
上記クラスを使う側
double_map.cc
#include <iostream> #include <string> #include "double_map.h" int main() { using Stbl = ScoreTable<std::string, std::string>; Stbl dmap; Stbl::Dmap set_map = {{"Tom", {{"english", 95}, {"math", 75}}}, {"Jaws", {{"english", 63}, {"math", 52}}}}; dmap.SetDmap(set_map); std::string student = "Tom"; std::string subject = "math"; std::cout << student << " : " << subject << " : score : "; std::cout << dmap.GetScore(student, subject) << std::endl; return 0; }
出力
Tom : math : score :75