#c #templates #pointers
#c #шаблоны #указатели
Вопрос:
Я столкнулся со странной ошибкой, связанной с классом шаблонов в C . Большую часть времени коды выполняются нормально, но в одном случае произошел сбой. Ниже приведены упрощенные коды:
template <class T>
class Class1
{
...
T *func();
...
};
// ---------------------------------------------------------------
template <class T>
T *Class1<T>::func(...)
{
...
string name = typeid(T).name();
T *ptr = a_queue.front(); // a_queue is of type "queue<T *>"
ptr->some_func(); // failed
...
}
// ---------------------------------------------------------------
Class1<Class2> class1;
class1.func();
Предположим, что Class1
специализируется на T
is Class2
и Class3
соответственно. В этом случае Class1<Class2>::func
, ptr
объявляется как Class3
указатель! Значит, тип небезопасен в классе шаблонов?
Есть идеи? Спасибо!
Редактировать:
Я добавил, string name = typeid(T).name()
тогда T
будет правильный тип ( Class2
), но при вызове функции-члена some_func
of Class2
возникает ошибка:
cannot access memory address at 0x10
[Решено] Окончательное редактирование 2011/11/09:
Я обнаружил проблему, она не связана с классом шаблонов, но вызвана удалением неправильного указателя, который не обновлен в той же функции с delete
и был помещен в очередь!
Комментарии:
1. Вы имеете в виду,
Class1
является специализированным? Вы не можете специализироватьсяT
— это просто тип. ВClass1<Class2>
,T
естьClass2
… когда вы получаете «странную ошибку», вы должны опубликовать эту ошибку, потому что компилятор C может напечатать любое количество странных ошибок.2. Да,
Class1
является специализированным. Я ожидаю, чтоT
вClass1<Class2>
должно бытьClass2
, но этоClass3
в моем случае. Нет прямого вывода ошибок, и мои коды довольно огромны, поэтому я не имею ни малейшего представления, как размещать ошибки.3. Вы выделяете память для
ptr
bynew
? Вы преобразуете выходные данныеfunc()
в другой тип? Вопрос очень неоднозначный.4. Извините за неоднозначный вопрос! Потому что это меня глубоко удивляет. Я не выделяю память для
ptr
, просто присваиваю ему адресClass2
объекта в очереди какT *ptr = a_queue.front()
.5. @LiDong, вам нужно придумать полный, минимальный фрагмент кода, который воспроизводил бы проблему, с которой вы столкнулись. Затем вы должны объяснить, какой результат вы получаете и какой результат вы ожидаете.
Ответ №1:
не удается получить доступ к адресу памяти в 0x10
Это эквивалентно ссылке на НУЛЕВОЙ указатель. Компилятор начал с некоторого T *ptr = 0
и попытался найти элемент (или vtable) T
со смещением 0x10, чтобы просмотреть память 0 0x10
. Так что я не думаю, что ваша проблема связана с типами шаблонов, а с a_queue.front()
содержащими NULL.
Комментарии:
1. Ваш ответ кажется правильным направлением для решения этой странной проблемы.
Ответ №2:
В вашем вопросе есть функция шаблона. Вы создали шаблон для обоих класса и функции?
template <typename T>
class Class1
{
template <typename U>
U *::func(... some argument of U...)
};
Это позволило бы вам вызвать Class1<Class2>::func(...some arg Class3...)
и попасть func<Class3>
внутрь Class1<Class2>
.
Комментарии:
1. Да, я создал оба шаблона
Class1
и его методfunc
сT
помощью.