Я пишу несколько классов шаблонов для синтаксического анализа некоторых текстовых файлов данных, и, как большинство из них, большинство ошибок синтаксического анализа будет связано с ошибками в файле данных, которые по большей части не написаны программистами, и поэтому нужно хорошее сообщение о том, почему приложение не удалось загрузить, например что-то вроде:
Анализ ошибок в примере .txt. Значение ( "notaninteger" ) ключа [MySectiom] не является допустимым значением int
Я могу обработать файлы, разделы и имена ключей из аргументов, переданных функции шаблона и членских классов в классе, однако я не уверен, как получить имя типа, который функция шаблона пытается конвертировать к.
Мой текущий код выглядит, со специализациями для простых строк и т.д.
template<typename T> T GetValue(const std::wstring §ion, const std::wstring &key)
{
std::map<std::wstring, std::wstring>::iterator it = map[section].find(key);
if(it == map[section].end())
throw ItemDoesNotExist(file, section, key)
else
{
try{return boost::lexical_cast<T>(it->second);}
//needs to get the name from T somehow
catch(...)throw ParseError(file, section, key, it->second, TypeName(T));
}
}
Идентификатор скорее не должен делать конкретные перегрузки для каждого типа, который могут использовать файлы данных, так как есть множество из них...
Также мне нужно решение, которое не несет никаких накладных расходов во время выполнения, если не возникает исключение, т.е. полностью компилируемое временное решение - это то, что я хочу, поскольку этот код называется тоннами раз, а время загрузки уже несколько длиннее.
EDIT: Хорошо, это решение, с которым я столкнулся:
У меня есть типы .h, содержащие следующие
#pragma once
template<typename T> const wchar_t *GetTypeName();
#define DEFINE_TYPE_NAME(type, name) \
template<>const wchar_t *GetTypeName<type>(){return name;}
Затем я могу использовать макрос DEFINE_TYPE_NAME в файлах cpp для каждого типа, с которым мне нужно иметь дело (например, в файле cpp, который определяет тип, который нужно начинать).
Затем компоновщик может найти подходящую специализацию шаблона, если он определен где-то, или выбросить ошибку компоновщика в противном случае, чтобы я мог добавить этот тип.