# pragma once
template<class T>
class Ptr
{
public:
Ptr( T * _t ): ptr(_t){}
~Ptr(){ delete ptr; }
protected:
T * ptr;
};
Если кто думает что это очень редкий случай, то я тоже так думал, пока не начал работать в компани в которой больше одного программиста на проект (а это везде) и пишут они асинхронные приложения.
желаю удачи! и не повторять таких вот ошибок которые так портят настроения
Здравствуйте, IROV.., Вы писали:
IRO>Все очень просто, я на днях убил пол рабочего дня на поиски бага, о котором читал только в умных книгах.
IRO>И бог знает сколько бы еще искал, если бы не случайность.
IRO>попробую привести минимально воспроизводимый код.
Здравствуйте, IROV.., Вы писали:
IRO>компилятор деляет одну виртуальную таблицу, и обьект я создаю по одному подобию а удаляется по другому.
Линкер, наверно, а не функтор?
People who are more than casually interested in computers should have at least some idea of what the underlying hardware is like. Otherwise the programs they write will be pretty weird (c) D.Knuth
Здравствуйте, gear nuke, Вы писали:
GN>Здравствуйте, IROV.., Вы писали:
IRO>>компилятор деляет одну виртуальную таблицу, и обьект я создаю по одному подобию а удаляется по другому.
GN>Линкер, наверно, а не функтор?
Вроде народ и так знает, что запрещено объявлять в разных единицах трансляции функции с одинаковыми именами... а вот теперь выясняется, что и дубликаты классов вредны для здоровья. Или всё-таки баг?
Здравствуйте, IROV.., Вы писали:
IRO>Все очень просто, я на днях убил пол рабочего дня на поиски бага, о котором читал только в умных книгах.
Тема давно раскрыта. Впредь, если вводишь сущность не входящую в публичный интерфейс, объявляй ее в анонимном пространстве имен. В противном случае, ты сам себе злобный Буратино.
Здравствуйте, Roman Odaisky, Вы писали:
RO>Вроде народ и так знает, что запрещено объявлять в разных единицах трансляции функции с одинаковыми именами... а вот теперь выясняется, что и дубликаты классов вредны для здоровья. Или всё-таки баг?
Проблема в том как себя убереч от этого? Единственое что я щас придумал так это анонимное пространство имен.
а по поводу того что дубликаты классов, надо попробовать убрать виртуальный деструктор. может подводит табличка?
Здравствуйте, Roman Odaisky, Вы писали:
RO>Вроде народ и так знает, что запрещено объявлять в разных единицах трансляции функции с одинаковыми именами... а вот теперь выясняется, что и дубликаты классов вредны для здоровья. Или всё-таки баг?
Дык, опаньки. 3.2 One Definition Rule действует на всё, что может торчать наружу из единицы трансляции:
5. There can be more than one definition of a class type (clause 9), enumeration type (7.2), inline function with external linkage (7.1.2), class template (clause 14), non-static function template (14.5.5), static data member of a class template (14.5.1.3), member function of a class template (14.5.1.1), or template specialization for which some template parameters are not specified (14.7, 14.5.4) in a program provided that each definition appears in a different translation unit, and provided the definitions satisfy the following requirements. Given such an entity named D defined in more than one translation unit, then
each definition of D shall consist of the same sequence of tokens; and
in each definition of D, corresponding names, looked up according to 3.4, shall refer to an entity defined within the definition of D, or shall refer to the same entity, after overload resolution (13.3) and after matching of partial template specialization (14.8.3), except that a name can refer to a const object with internal or no linkage if the object has the same integral or enumeration type in all definitions of D, and the object is initialized with a constant expression (5.19), and the value (but not the address) of the object is used, and the object has the same value in all definitions of D; and
in each definition of D, the overloaded operators referred to, the implicit calls to conversion functions, constructors, operator new functions and operator delete functions, shall refer to the same function, or to a function defined within the definition of D; and
in each definition of D, a default argument used by an (implicit or explicit) function call is treated as if its token sequence were present in the definition of D; that is, the default argument is subject to the three requirements described above (and, if the default argument has sub-expressions with default arguments, this requirement applies recursively).[25]
[25] 8.3.6 describes how default argument names are looked up.
if D is a class with an implicitly-declared constructor (12.1), it is as if the constructor was implicitly defined in every translation unit where it is used, and the implicit definition in every translation unit shall call the same constructor for a base class or a class member of D. [Example:
// translation unit 1:struct X {
X(int);
X(int, int);
};
X::X(int = 0) { }
class D: public X { };
// X(int) called by D()
D d2;
// translation unit 2:struct X {
X(int);
X(int, int);
};
X::X(int = 0, int = 0) { }
// X(int, int) called by D();class D: public X { };
// D()’s implicit definition
// violates the ODR
—end example] If D is a template, and is defined in more than one translation unit, then the last four requirements from the list above shall apply to names from the template’s enclosing scope used in the template definition (14.6.3), and also to dependent names at the point of instantiation (14.6.2). If the definitions of D satisfy all these requirements, then the program shall behave as if there were a single definition of D. If the definitions of D do not satisfy these requirements, then the behavior is undefined.