<?xml version="1.0" encoding="UTF-8"?><rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:atom="http://www.w3.org/2005/Atom" version="2.0"><channel><title><![CDATA[Verweis auf nicht-statischen Member (template,using,ctor,unwichtig&#x2F;komisch)]]></title><description><![CDATA[<p>tag.<br />
der fehler ist nicht besonders schwerwiegend, aber er regt mich einfach auf.<br />
ich weiß nicht nach was ich suchen soll, um das thema im forum zu finden.</p>
<p>folgender abschnitt des quellcodes wird nicht verändert:</p>
<pre><code class="language-cpp">#include &lt;list&gt;

template&lt; class P &gt; class TMsg
{
public:
	typedef int code_t; typedef P	param_t;
private:
	code_t	cv;	param_t pv;
public:
	code_t const get_code() const { return cv; }
	param_t const get_param() const { return pv; }
public:
	TMsg() : cv(0), pv(0) {}
	TMsg( TMsg const &amp;r ) : cv(r.cv), pv(r.pv) {}
	TMsg( code_t c, param_t p ) : cv(c), pv(p) {}
	~TMsg() {}
};
</code></pre>
<p>jetzt kommt erstmal die &quot;class Test&quot; und &quot;main()&quot;, wie ich mir vorstelle, dass sie funktionieren sollten.<br />
diese version wird KOMPILIERT!</p>
<pre><code class="language-cpp">class Test
{
public:
	typedef TMsg&lt;Test const*&gt;	msg_t;
	typedef std::list&lt; msg_t &gt;	protocol_t;
	struct MSG { enum { UNKNOWN_ERROR, INVALID_METHOD, MOVE_MOUSE }; };

public:
	void report( protocol_t &amp;prot )
	{
		prot.push_back( msg_t( MSG::UNKNOWN_ERROR, this ) ); //!!
	}
};

int main()
{
	Test t;
	Test::protocol_t prot;
	t.report( prot );
	return 0;
};
</code></pre>
<p>jetzt soll &quot;class Test&quot; aber von einer basisklasse abgeleitet werden, die die definition der &quot;struct enum MSG&quot;, &quot;typename msg_t&quot; und &quot;typename protocol_t&quot; schon mitbringt und weiter über virtuelle methoden verfügt.<br />
beispiel für die basisklasse und die resultierende &quot;main()&quot;:</p>
<pre><code class="language-cpp">class Base
{
public:
	typedef TMsg&lt;Base const*&gt;	msg_t;
	typedef std::list&lt; msg_t &gt;	protocol_t;
	struct MSG { enum { UNKNOWN_ERROR, INVALID_METHOD, MOVE_MOUSE }; };
	virtual int do_sth() { return -1; }
	virtual ~Base() {}
};
/* ... definition von &quot;template class TTest&quot; */
int main()
{
	typedef TTest&lt;Base&gt;	Test;
	Test t;
	Test::protocol_t prot;
	t.report( prot );
	return 0;
};
</code></pre>
<p>schreibt man &quot;class Test&quot; zu &quot;template class TTest&quot; um, bekommt man folgendes:<br />
( wird NICHT KOMPILIERT! )</p>
<pre><code class="language-cpp">template &lt; class B &gt;
class TTest : public B
{
public:
	using typename B::msg_t;
	using typename B::protocol_t;
	using typename B::MSG;

public:
	void report( protocol_t &amp;prot )
	{
		prot.push_back( msg_t( MSG::UNKNOWN_ERROR, static_cast&lt;B*&gt;(this) ) ); //!!
	}
};
</code></pre>
<p>Visual C++ 2008 EE meldet dann folgenden Fehler:</p>
<pre><code>1&gt;main.cpp(75) : error C2597: Ungültiger Verweis auf nicht-statischen Member 'TTest&lt;B&gt;::msg_t'
1&gt;        with
1&gt;        [
1&gt;            B=Base
1&gt;        ]
1&gt;        main.cpp(74): Bei der Kompilierung der  Klassen-template der void TTest&lt;B&gt;::report(std::list&lt;_Ty&gt; &amp;)-Memberfunktion
1&gt;        with
1&gt;        [
1&gt;            B=Base,
1&gt;            _Ty=Base::msg_t
1&gt;        ]
1&gt;main.cpp(105): Siehe Verweis auf die Instanziierung der gerade kompilierten Klassen-template &quot;TTest&lt;B&gt;&quot;.
1&gt;        with
1&gt;        [
1&gt;            B=Base
1&gt;        ]
</code></pre>
<p>ich hab den fehler bereits behoben (durch ausprobieren)<br />
und zwar hab ich die konstruktion der &quot;msg&quot; einfach aus dem ausdruck genommen.<br />
( wird KOMPILIERT! )</p>
<pre><code class="language-cpp">template &lt; class B &gt;
class TTest : public B
{
public:
	using typename B::msg_t;
	using typename B::protocol_t;
	using typename B::MSG;

public:
	void report( protocol_t &amp;prot )
	{
		msg_t msg( MSG::UNKNOWN_ERROR, static_cast&lt;B*&gt;(this) );
		prot.push_back( msg ); //!!
	}
};
</code></pre>
<p>trotzdem stellt sich die frage, warum die vorherige version nicht funktioniert hat...</p>
<p>tests mit anderen compileren:</p>
<p>Visual C++ 6.0 kompiliert genauso, nur die fehlermeldung ist anders:</p>
<pre><code>C:\prog\eigene\VCPP\Rechner2x2_4\ctor_tst_2008_10_09\main.cpp(74) : error C2064: Ausdruck ergibt keine Funktion
        C:\prog\eigene\VCPP\Rechner2x2_4\ctor_tst_2008_10_09\main.cpp(73) : Bei der Kompilierung der Member-Funktion 'void __thiscall TTest&lt;class Base&gt;::report(
		class std::list&lt;class TMsg&lt;class Base const *&gt;, class std::allocator&lt;class TMsg&lt;class Base const *&gt; &gt; &gt; &amp;)' der Klassenvorlage
</code></pre>
<p>mit Dev-C++ 4.9.9.2 funktionieren beide template versionen nicht.<br />
mit OpenWatcom 1.6 funktioniert gar nichts.</p>
]]></description><link>https://www.c-plusplus.net/forum/topic/224442/verweis-auf-nicht-statischen-member-template-using-ctor-unwichtig-komisch</link><generator>RSS for Node</generator><lastBuildDate>Fri, 02 Oct 2026 16:01:37 GMT</lastBuildDate><atom:link href="https://www.c-plusplus.net/forum/topic/224442.rss" rel="self" type="application/rss+xml"/><pubDate>Thu, 09 Oct 2008 14:55:49 GMT</pubDate><ttl>60</ttl><item><title><![CDATA[Reply to Verweis auf nicht-statischen Member (template,using,ctor,unwichtig&#x2F;komisch) on Thu, 09 Oct 2008 14:55:49 GMT]]></title><description><![CDATA[<p>tag.<br />
der fehler ist nicht besonders schwerwiegend, aber er regt mich einfach auf.<br />
ich weiß nicht nach was ich suchen soll, um das thema im forum zu finden.</p>
<p>folgender abschnitt des quellcodes wird nicht verändert:</p>
<pre><code class="language-cpp">#include &lt;list&gt;

template&lt; class P &gt; class TMsg
{
public:
	typedef int code_t; typedef P	param_t;
private:
	code_t	cv;	param_t pv;
public:
	code_t const get_code() const { return cv; }
	param_t const get_param() const { return pv; }
public:
	TMsg() : cv(0), pv(0) {}
	TMsg( TMsg const &amp;r ) : cv(r.cv), pv(r.pv) {}
	TMsg( code_t c, param_t p ) : cv(c), pv(p) {}
	~TMsg() {}
};
</code></pre>
<p>jetzt kommt erstmal die &quot;class Test&quot; und &quot;main()&quot;, wie ich mir vorstelle, dass sie funktionieren sollten.<br />
diese version wird KOMPILIERT!</p>
<pre><code class="language-cpp">class Test
{
public:
	typedef TMsg&lt;Test const*&gt;	msg_t;
	typedef std::list&lt; msg_t &gt;	protocol_t;
	struct MSG { enum { UNKNOWN_ERROR, INVALID_METHOD, MOVE_MOUSE }; };

public:
	void report( protocol_t &amp;prot )
	{
		prot.push_back( msg_t( MSG::UNKNOWN_ERROR, this ) ); //!!
	}
};

int main()
{
	Test t;
	Test::protocol_t prot;
	t.report( prot );
	return 0;
};
</code></pre>
<p>jetzt soll &quot;class Test&quot; aber von einer basisklasse abgeleitet werden, die die definition der &quot;struct enum MSG&quot;, &quot;typename msg_t&quot; und &quot;typename protocol_t&quot; schon mitbringt und weiter über virtuelle methoden verfügt.<br />
beispiel für die basisklasse und die resultierende &quot;main()&quot;:</p>
<pre><code class="language-cpp">class Base
{
public:
	typedef TMsg&lt;Base const*&gt;	msg_t;
	typedef std::list&lt; msg_t &gt;	protocol_t;
	struct MSG { enum { UNKNOWN_ERROR, INVALID_METHOD, MOVE_MOUSE }; };
	virtual int do_sth() { return -1; }
	virtual ~Base() {}
};
/* ... definition von &quot;template class TTest&quot; */
int main()
{
	typedef TTest&lt;Base&gt;	Test;
	Test t;
	Test::protocol_t prot;
	t.report( prot );
	return 0;
};
</code></pre>
<p>schreibt man &quot;class Test&quot; zu &quot;template class TTest&quot; um, bekommt man folgendes:<br />
( wird NICHT KOMPILIERT! )</p>
<pre><code class="language-cpp">template &lt; class B &gt;
class TTest : public B
{
public:
	using typename B::msg_t;
	using typename B::protocol_t;
	using typename B::MSG;

public:
	void report( protocol_t &amp;prot )
	{
		prot.push_back( msg_t( MSG::UNKNOWN_ERROR, static_cast&lt;B*&gt;(this) ) ); //!!
	}
};
</code></pre>
<p>Visual C++ 2008 EE meldet dann folgenden Fehler:</p>
<pre><code>1&gt;main.cpp(75) : error C2597: Ungültiger Verweis auf nicht-statischen Member 'TTest&lt;B&gt;::msg_t'
1&gt;        with
1&gt;        [
1&gt;            B=Base
1&gt;        ]
1&gt;        main.cpp(74): Bei der Kompilierung der  Klassen-template der void TTest&lt;B&gt;::report(std::list&lt;_Ty&gt; &amp;)-Memberfunktion
1&gt;        with
1&gt;        [
1&gt;            B=Base,
1&gt;            _Ty=Base::msg_t
1&gt;        ]
1&gt;main.cpp(105): Siehe Verweis auf die Instanziierung der gerade kompilierten Klassen-template &quot;TTest&lt;B&gt;&quot;.
1&gt;        with
1&gt;        [
1&gt;            B=Base
1&gt;        ]
</code></pre>
<p>ich hab den fehler bereits behoben (durch ausprobieren)<br />
und zwar hab ich die konstruktion der &quot;msg&quot; einfach aus dem ausdruck genommen.<br />
( wird KOMPILIERT! )</p>
<pre><code class="language-cpp">template &lt; class B &gt;
class TTest : public B
{
public:
	using typename B::msg_t;
	using typename B::protocol_t;
	using typename B::MSG;

public:
	void report( protocol_t &amp;prot )
	{
		msg_t msg( MSG::UNKNOWN_ERROR, static_cast&lt;B*&gt;(this) );
		prot.push_back( msg ); //!!
	}
};
</code></pre>
<p>trotzdem stellt sich die frage, warum die vorherige version nicht funktioniert hat...</p>
<p>tests mit anderen compileren:</p>
<p>Visual C++ 6.0 kompiliert genauso, nur die fehlermeldung ist anders:</p>
<pre><code>C:\prog\eigene\VCPP\Rechner2x2_4\ctor_tst_2008_10_09\main.cpp(74) : error C2064: Ausdruck ergibt keine Funktion
        C:\prog\eigene\VCPP\Rechner2x2_4\ctor_tst_2008_10_09\main.cpp(73) : Bei der Kompilierung der Member-Funktion 'void __thiscall TTest&lt;class Base&gt;::report(
		class std::list&lt;class TMsg&lt;class Base const *&gt;, class std::allocator&lt;class TMsg&lt;class Base const *&gt; &gt; &gt; &amp;)' der Klassenvorlage
</code></pre>
<p>mit Dev-C++ 4.9.9.2 funktionieren beide template versionen nicht.<br />
mit OpenWatcom 1.6 funktioniert gar nichts.</p>
]]></description><link>https://www.c-plusplus.net/forum/post/1596372</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/1596372</guid><dc:creator><![CDATA[wandrer]]></dc:creator><pubDate>Thu, 09 Oct 2008 14:55:49 GMT</pubDate></item></channel></rss>