initialize static data member in derived class

Programmiersprachen, APIs, Bibliotheken, Open Source Engines, Debugging, Quellcode Fehler und alles was mit praktischer Programmierung zu tun hat.
Antworten
kaiserludi
Establishment
Beiträge: 467
Registriert: 18.04.2002, 15:31

initialize static data member in derived class

Beitrag von kaiserludi »

Moin.

Ich habe eine abstrakte Basis Klasse CustomType.
Diese hat unter anderem einen static const unsigned char mTypecode;.
CustomType gilt als Interface für die Serialisierung von custom Types und deklariert die Callback-API, die Typen einer App implementieren müssen, damit sie aus der Lib heraus per Callback (de-)serialisiert, verglichen, dupliziert, oder als String representiert werden können.

Jeder custom type muss nun laut Serialisierungs-Protokoll einen eigenen typecode haben, der gleiche type aber immer den gleichen typecode, sprich, wenn Klasse AA und Klasse AB beide von Klasse A erben, müssen alle Instanzen von AA den gleichen typecode nutzen, der sich aber von dem unterscheidet, den alle Instanzen der Klasse AB nutzten.

Das wollte ich umsetzen, in dem ich eben den erwähnten statischen mTypecode in der Mutterklasse habe und jede erbende Klasse diese Konstante anders initialisieren lasse.

Leider führt das zu warning C4356: static data member cannot be initialized via derived class

Dummerweise will ich ja genau das: einen static data member in der erbenden Klasse und nicht in der Basisklasse initialisieren.

Laut google werden wohl statische Member nicht wirklich vererbt, sondern alle erbenden Klassen aller Hierachieebenen greifen auf die selbe Variable zu, was natürlich nicht meine Intention ist.

Ideen, wie ich das oben erklärte Feature am elegantesten implementieren kann, ohne über diese Einschränkung durch die Sprache zu stolpern?
"Mir ist auch klar, dass der Tag, an dem ZFX und Developia zusammengehen werden der selbe Tag sein wird, an dem DirectGL rauskommt."
DirectGL, endlich ist es da
:)

"According to the C++ standard, it's "undefined". That's a technical term that means, in theory, anything can happen: the program can crash, or keep running but generate garbage results, or send Bjarne Stroustrup an e-mail saying how ugly you are and how funny your mother dresses you." :shock:[/size]
Alexander Kornrumpf
Moderator
Beiträge: 2119
Registriert: 25.02.2009, 13:37

Re: initialize static data member in derived class

Beitrag von Alexander Kornrumpf »

Eine (virtuelle) Methode, die eine Konstante zurückgibt?
Benutzeravatar
Krishty
Establishment
Beiträge: 8268
Registriert: 26.02.2009, 11:18
Benutzertext: state is the enemy
Kontaktdaten:

Re: initialize static data member in derived class

Beitrag von Krishty »

So ist es – virtual unsigned char typecode() const = 0; in die Basisklasse.

Oder in der Basisklasse ein unsigned char const-Attribut (nicht-static) anlegen, das im K’tor gefüllt wird. Damit wäre jeder K’tor einer ableitenden Klasse gezwungen, einen Wert einzutragen, den jede Instanz der abgeleiteten Klasse mit sich herumträgt. Würde ich aber nur machen, falls das Rausfinden der ID geschwindigkeitskritisch wäre – wovon bei Serialisierung nicht auszugehen ist. Darum nochmal: rein virtuelle Funktion in die Basisklasse.

Gruß, Ky
seziert Ace Combat, Driver, und S.T.A.L.K.E.R.   —   rendert Sterne
kaiserludi
Establishment
Beiträge: 467
Registriert: 18.04.2002, 15:31

Re: initialize static data member in derived class

Beitrag von kaiserludi »

Das wären dann ja aber keine statischen Variablen. Das heißt, jede Instanz könte den Wert auf was anderes setzen. Außerdem wäre die Variable selbst nicht konstant und könnte jederzeit geändert werden. Damit muss ein Implemntierer einer erbenden Klasse also doch wieder aufpassen, dass er auch wirklich nur im Konstruktor schreibend darauf zugreift und zwar in jedem Konstruktoraufruf mit dem gleichen Wert.
ideal wäre ein C#-like readonly als statische Variable, initialisiert in einem statischen Konstruktot udn das ganz pure virtuell, damit es auch initalisiert werden muss, aber das überschreitet wohl die Grenzen der Sprachmittel, die C++ zur Verfügung stellt :cry:
"Mir ist auch klar, dass der Tag, an dem ZFX und Developia zusammengehen werden der selbe Tag sein wird, an dem DirectGL rauskommt."
DirectGL, endlich ist es da
:)

"According to the C++ standard, it's "undefined". That's a technical term that means, in theory, anything can happen: the program can crash, or keep running but generate garbage results, or send Bjarne Stroustrup an e-mail saying how ugly you are and how funny your mother dresses you." :shock:[/size]
Benutzeravatar
Krishty
Establishment
Beiträge: 8268
Registriert: 26.02.2009, 11:18
Benutzertext: state is the enemy
Kontaktdaten:

Re: initialize static data member in derived class

Beitrag von Krishty »

Welchen der beiden Vorschläge meinst du damit?

Und wenn du von statischen Variablen sprichst, musst du daran denken, dass diese Variablen für die Klasse, in der sie deklariert wurden, gelten. Wenn du die ID eines Objekts abfragst, weißt du aber nicht, zu welcher Klasse es gehört – willst du auch garnicht, sonst hättest du dich nicht für Polymorphie als Lösungsansatz entschieden. Darum ist es per Definition unmöglich, eine statische Variable einer abgeleiteten Klasse durch eine Instanz dieser abzufragen, so lange du nicht durch typeid und dynamic_cast garantieren kannst, dass diese Instanz zu einer bestimmten, dir bekannten Klasse gehört.
seziert Ace Combat, Driver, und S.T.A.L.K.E.R.   —   rendert Sterne
kaiserludi
Establishment
Beiträge: 467
Registriert: 18.04.2002, 15:31

Re: initialize static data member in derived class

Beitrag von kaiserludi »

Krishty hat geschrieben:Welchen der beiden Vorschläge meinst du damit?
Beide.

Ich seh schon: Mein Ziel scheint nicht erreichbar zu sein.
"Mir ist auch klar, dass der Tag, an dem ZFX und Developia zusammengehen werden der selbe Tag sein wird, an dem DirectGL rauskommt."
DirectGL, endlich ist es da
:)

"According to the C++ standard, it's "undefined". That's a technical term that means, in theory, anything can happen: the program can crash, or keep running but generate garbage results, or send Bjarne Stroustrup an e-mail saying how ugly you are and how funny your mother dresses you." :shock:[/size]
Benutzeravatar
Krishty
Establishment
Beiträge: 8268
Registriert: 26.02.2009, 11:18
Benutzertext: state is the enemy
Kontaktdaten:

Re: initialize static data member in derived class

Beitrag von Krishty »

Falls du unbedingt was pro Typ Einzigartiges brauchst, könntest du ja das Ergebnis von typeid nutzen. Aber Reflection ist bei C++ eben wirklich spärlich.
seziert Ace Combat, Driver, und S.T.A.L.K.E.R.   —   rendert Sterne
Benutzeravatar
dot
Establishment
Beiträge: 1734
Registriert: 06.03.2004, 18:10
Echter Name: Michael Kenzel
Kontaktdaten:

Re: initialize static data member in derived class

Beitrag von dot »

Statische Member werden nicht vererbt, auch in C# nicht afaik. Wenn du mal genau drüber nachdenkst wirst du merken dass das gar keinen Sinn machen würde. typeid könnte eine Lösung sein, denn darüber bekommst du einen eindeutigen String zu jeder Klasse. Aber warum kannst du nicht einfach Interfaces verwenden:

Code: Alles auswählen

class Serializable
{
  ...
  virtual void Serialize(Stream& stream) const = 0;
  virtual void Serialize(string& str) const = 0;
};

template <typename T>
class Comparable
{
  ...
  virtual bool Compare(const T* b) const = 0;
};

template <typename T>
class Cloneable
{
  ...
  virtual T* Clone() const = 0;
};
Alexander Kornrumpf
Moderator
Beiträge: 2119
Registriert: 25.02.2009, 13:37

Re: initialize static data member in derived class

Beitrag von Alexander Kornrumpf »

kaiserludi hat geschrieben:Das wären dann ja aber keine statischen Variablen. Das heißt, jede Instanz könte den Wert auf was anderes setzen. Außerdem wäre die Variable selbst nicht konstant und könnte jederzeit geändert werden. Damit muss ein Implemntierer einer erbenden Klasse also doch wieder aufpassen, dass er auch wirklich nur im Konstruktor schreibend darauf zugreift und zwar in jedem Konstruktoraufruf mit dem gleichen Wert.
ideal wäre ein C#-like readonly als statische Variable, initialisiert in einem statischen Konstruktot udn das ganz pure virtuell, damit es auch initalisiert werden muss, aber das überschreitet wohl die Grenzen der Sprachmittel, die C++ zur Verfügung stellt :cry:
Also mit einer statischen Variable kann es nicht gehen. Wenn die Funktion aus einem "return 1234;" besteht kann da auch nicht jederzeit was geändert werden. Für den Anwender der Klasse ist das meiner Meinung nach Narrensicher und besser als jede Lüsung die irgendwas im Konstruktor zuweist. Wo du die Magic Number stehen hast (Konstruktor oder Funktionsrumpf) ist ja erstmal egal, wichtig ist dass es genau eine Stelle ist.

Wogegen du dich nicht schützen kannst ist dass jemand die Methode bösartig mit "return rand()" überläd. Gegen Bösartigkeit kannst du dich aber auch bei der anderen Lösung nicht schützen, da jemand auch bei jeder anderen Lösung die ID von einer anderen Klasse hijacken und damit unheil anrichten könnte. Das kann sogar versehentlich passieren während ich die Chance dass jemand einen wohldokumentierten Einzeiler aus Versehen dämlich überläd für verschwindend gering halte.

Vielleicht solltest du dir um das Problem der Uniqueness mehr Sorgen machen.
kaiserludi
Establishment
Beiträge: 467
Registriert: 18.04.2002, 15:31

Re: initialize static data member in derived class

Beitrag von kaiserludi »

dot hat geschrieben:Aber warum kannst du nicht einfach Interfaces verwenden:
Weil ich davon alleine noch keine ID habe, mit der ein anderes Programm (auch in einer anderen Sprache) dann erkennen kann, wie es die serialisierten Daten zu interpretieren hat.

@Alexander:
Ich hätte es für die Implementierer der erbenden Klassen eben am liebsten möglicsht narrensicher, aber scheinbar kann ich nur per Kommnetar darauf hinweisen, dass die gleiche Klasse immer diegleiche ID verwenden sollte.

Was die Uniqueness angeht: Da habe ich die Hoffnun eigentlich von vornerherein nie gehabt, das absolut sicherstellen zu können.
Ich speichere die Callbacks derzeit nach ID. Das heißt, es kann sich für jeden Callback nur eine Funktion pro ID anmelden und wenn man sich für eine Callback anmeldet, muss man sich für alle anmelden. Wenn 2 verschiedene Klassensich unter der gleichen ID anmelden wollen, bekommt die erste den Vorzug.
"Mir ist auch klar, dass der Tag, an dem ZFX und Developia zusammengehen werden der selbe Tag sein wird, an dem DirectGL rauskommt."
DirectGL, endlich ist es da
:)

"According to the C++ standard, it's "undefined". That's a technical term that means, in theory, anything can happen: the program can crash, or keep running but generate garbage results, or send Bjarne Stroustrup an e-mail saying how ugly you are and how funny your mother dresses you." :shock:[/size]
Alexander Kornrumpf
Moderator
Beiträge: 2119
Registriert: 25.02.2009, 13:37

Re: initialize static data member in derived class

Beitrag von Alexander Kornrumpf »

Mal angenommen man könne statische Konstanten in der Abgeleiteteten Klasse neu definieren. Dann kannst du nicht garantieren dass das nicht jemand vergisst.

Mit einer rein virtuellen Funktion bist du wenigstens sicher dass der Erbe sich überhaupt gedanken macht. Wenn er es dann schafft eine Methode die heißt "getUniqueTypeCodeWhichIsConstantOverAllInstancesOfThisType" und aus einer Zeile besteht zu verseppeln, hat er es vielleicht auch einfach nicht anders verdient. Die Basisklasse kann den Aufruf ja in einer nicht virtuellen Methode wrappen um den elend langen Namen loszuwerden. Wer eine nicht virtuelle Methode überläd ist auch selbst schuld.
Benutzeravatar
Krishty
Establishment
Beiträge: 8268
Registriert: 26.02.2009, 11:18
Benutzertext: state is the enemy
Kontaktdaten:

Re: initialize static data member in derived class

Beitrag von Krishty »

Alexander Kornrumpf hat geschrieben:Wer eine nicht virtuelle Methode überläd ist auch selbst schuld.
… seit Einführung des override-Schlüsselworts, für das ich hier einfach nochmal werbe :)

class Base {
    virtual void foo(int const * x);
};

class Derived : Base {
    virtual void foo(int * const x) override; // Compiler-Fehler
};
seziert Ace Combat, Driver, und S.T.A.L.K.E.R.   —   rendert Sterne
Benutzeravatar
BeRsErKeR
Establishment
Beiträge: 689
Registriert: 27.04.2002, 22:01

Re: initialize static data member in derived class

Beitrag von BeRsErKeR »

Krishty hat geschrieben:Oder in der Basisklasse ein unsigned char const-Attribut (nicht-static) anlegen, das im K’tor gefüllt wird. Damit wäre jeder K’tor einer ableitenden Klasse gezwungen, einen Wert einzutragen, den jede Instanz der abgeleiteten Klasse mit sich herumträgt.
kaiserludi hat geschrieben:Das wären dann ja aber keine statischen Variablen. Das heißt, jede Instanz könte den Wert auf was anderes setzen. Außerdem wäre die Variable selbst nicht konstant und könnte jederzeit geändert werden.
Wenn du für Krishtys Vorschlag die Variable in der Basisklasse private anlegst kann keine abgeleitete Klasse bzw. Instanzen davon was an dem Wert ändern. Nur der Parameter, der dem Konstruktor der Basisklasse mitgegeben wird legt den Typcode fest und das geht dann nur einmalig beim Anlegen einer Instanz. Da der Konstruktor für alle Instanzen identisch ist, besitzen auch alle Instanzen den selben Typcode. Es ist also genau das was du willst. Bei deiner Idee mit statischen Variablen müsstest du den Wert auch irgendwo einmalig initialisieren und hier ist es eigentlich genauso. Es existiert zwar für jede Instanz eine eigene Variable, aber es ist gewährleistet, dass Instanzen der selben Klasse auch den selben Wert für den Typcode nutzen. Der Wert kann nur in der Initialisierungsliste des Konstruktors der abgeleiteten Klasse festgelegt werden über den Aufruf des Basisklassen-Konstruktors mit dem entsprechenden Parameter. Problem gelöst.

Und sollte jemand wirklich so dumm sein, zwei verschiedene Konstruktoren in der abgeleiteten Klasse unterzubringen, die verschiedene Werte an die Basisklasse übergeben, dann ist er halt selbst Schuld. Was dieser Parameter bedeutet, sollte sowieso dokumentiert sein/werden, von daher sollte das recht eindeutig sein und wer würde denn auf die Idee kommen sowas zu machen? Das wäre ja wirklich grober Sadismus. ;)
Ohne Input kein Output.
Benutzeravatar
Krishty
Establishment
Beiträge: 8268
Registriert: 26.02.2009, 11:18
Benutzertext: state is the enemy
Kontaktdaten:

Re: initialize static data member in derived class

Beitrag von Krishty »

BeRsErKeR hat geschrieben:Da der Konstruktor für alle Instanzen identisch ist, besitzen auch alle Instanzen den selben Typcode.
So einfach ist es leider doch nicht:

Derived::Derived()
    : Base(rand())
{ }


Hier haben dann doch die meisten Intanzen unterschiedliche Codes. Ist auch garnicht so einfach auszuschließen, falls jemand die ID in eine Funktion packt und man noch kein constexpr hat. Man könnte es in einem Template verschachteln um den Fall auszuschließen:

template <unsigned char itsID> class BaseWithFixedID
    : public Base
{
public:
    static unsigned char const ID = itsID;
protected:
    BaseWithFixedID()
        : Base(ID)
    { }
};

class Derived
    : public BaseWithFixedID<123>
{
[…]
seziert Ace Combat, Driver, und S.T.A.L.K.E.R.   —   rendert Sterne
Benutzeravatar
BeRsErKeR
Establishment
Beiträge: 689
Registriert: 27.04.2002, 22:01

Re: initialize static data member in derived class

Beitrag von BeRsErKeR »

Ich glaube ein Template wäre tatsächlich eine gute Wahl, da man keinen Overhead zur Laufzeit hat und da es das von dir genannte "rand-Problem" löst. Letzteres hätte ich glatt unterschlagen. ;)
Ohne Input kein Output.
kaiserludi
Establishment
Beiträge: 467
Registriert: 18.04.2002, 15:31

Re: initialize static data member in derived class

Beitrag von kaiserludi »

Das Template hat mich jetzt auch als beste Lösung überzeugt und wurde bereits implementiert. 8-)
"Mir ist auch klar, dass der Tag, an dem ZFX und Developia zusammengehen werden der selbe Tag sein wird, an dem DirectGL rauskommt."
DirectGL, endlich ist es da
:)

"According to the C++ standard, it's "undefined". That's a technical term that means, in theory, anything can happen: the program can crash, or keep running but generate garbage results, or send Bjarne Stroustrup an e-mail saying how ugly you are and how funny your mother dresses you." :shock:[/size]
Alexander Kornrumpf
Moderator
Beiträge: 2119
Registriert: 25.02.2009, 13:37

Re: initialize static data member in derived class

Beitrag von Alexander Kornrumpf »

Mich würde interessieren ob und wie du verhinderst dass jemand von Base statt von BaseWithFixedID erbt. Spontan fällt mir nur ein den Konstruktor von Base private zu deklarieren und mit friend zu arbeiten. Dann könnte das tatsächlich eine runde Sache sein.
kaiserludi
Establishment
Beiträge: 467
Registriert: 18.04.2002, 15:31

Re: initialize static data member in derived class

Beitrag von kaiserludi »

Alexander Kornrumpf hat geschrieben:Mich würde interessieren ob und wie du verhinderst dass jemand von Base statt von BaseWithFixedID erbt. Spontan fällt mir nur ein den Konstruktor von Base private zu deklarieren und mit friend zu arbeiten. Dann könnte das tatsächlich eine runde Sache sein.
Jap, schlage gerade die Syntax nach, wie ich eine template class als friend angebe :mrgreen:
EDIT: ah, "template" muss vor "friend" stehen, damit der Compiler versteht, was ich will.
"Mir ist auch klar, dass der Tag, an dem ZFX und Developia zusammengehen werden der selbe Tag sein wird, an dem DirectGL rauskommt."
DirectGL, endlich ist es da
:)

"According to the C++ standard, it's "undefined". That's a technical term that means, in theory, anything can happen: the program can crash, or keep running but generate garbage results, or send Bjarne Stroustrup an e-mail saying how ugly you are and how funny your mother dresses you." :shock:[/size]
Benutzeravatar
Biolunar
Establishment
Beiträge: 154
Registriert: 27.06.2005, 17:42
Alter Benutzername: dLoB

Re: initialize static data member in derived class

Beitrag von Biolunar »

kaiserludi hat geschrieben:
Alexander Kornrumpf hat geschrieben:Mich würde interessieren ob und wie du verhinderst dass jemand von Base statt von BaseWithFixedID erbt. Spontan fällt mir nur ein den Konstruktor von Base private zu deklarieren und mit friend zu arbeiten. Dann könnte das tatsächlich eine runde Sache sein.
Jap, schlage gerade die Syntax nach, wie ich eine template class als friend angebe :mrgreen:
EDIT: ah, "template" muss vor "friend" stehen, damit der Compiler versteht, was ich will.
Haha, das vergesse ich auch immer :D
kaiserludi
Establishment
Beiträge: 467
Registriert: 18.04.2002, 15:31

Re: initialize static data member in derived class

Beitrag von kaiserludi »

So, neues Problem.

Ich habe folgendes Makro:

Code: Alles auswählen

template<bool> struct CompileTimeAssertTrue;
template<> struct CompileTimeAssertTrue<true> {};

#define COMPILE_TIME_ASSERT_TRUE(expr) {CompileTimeAssertTrue<(expr)> ASSERTION_FAILED; (void)ASSERTION_FAILED;}
#define COMPILE_TIME_ASSERT_TRUE_MSG(expr, msg) {CompileTimeAssertTrue<(expr)> ASSERTION_FAILED_##msg; (void)ASSERTION_FAILED_##msg;}
Dazu dieses struct template:

Code: Alles auswählen

template<typename CType, nByte customTypeCode = 0> struct ConfirmAllowed;
Dieses hat einen Haufen Spezialisierungen, unter anderem diese neu eingeführte partielle Spezialiserung für custom types, welche als einzige Gebrauch von dem neuen default Parameter customTypeCode macht:

Code: Alles auswählen

template<nByte customTypeCode> struct ConfirmAllowed<CustomType<customTypeCode>, customTypeCode>
{
	typedef CustomType<customTypeCode> type;
	typedef CustomType<customTypeCode> scalarType;
	static const unsigned int dimensions = 0;
	static const nByte typeName = EG_CUSTOM;
	static const nByte customTypeName = customTypeCode;
};
Schließlich gibt es folgende Konstruktoren:

Code: Alles auswählen

	template <class Etype, nByte customTypeCode>
	ValueObject<Etype, customTypeCode>::ValueObject(typename ConfirmAllowed<Etype, customTypeCode>::type data)
	{
		COMPILE_TIME_ASSERT_TRUE_MSG(!ConfirmAllowed<Etype, customTypeCode>::dimensions, ERROR_THIS_OVERLOAD_IS_ONLY_FOR_SCALAR_TYPES);
		set(&data, ConfirmAllowed<Etype, customTypeCode>::typeName, ConfirmAllowed<Etype, customTypeCode>::customTypeName, true);
	}

	template <class Etype, nByte customTypeCode>
	ValueObject<Etype*, customTypeCode>::ValueObject(typename ConfirmAllowed<Etype*, customTypeCode>::type data, short size)
	{
		COMPILE_TIME_ASSERT_TRUE_MSG(ConfirmAllowed<Etype*, customTypeCode>::dimensions==1, ERROR_THIS_OVERLOAD_IS_ONLY_FOR_1D_ARRAYS);
		set(data, ConfirmAllowed<Etype*, customTypeCode>::typeName, ConfirmAllowed<Etype*, customTypeCode>::customTypeName, size, true);
	}

	template <class Etype, nByte customTypeCode>
	ValueObject<Etype*, customTypeCode>::ValueObject(typename ConfirmAllowed<Etype*, customTypeCode>::type data, const short* const sizes)
	{
		COMPILE_TIME_ASSERT_TRUE_MSG((bool)ConfirmAllowed<Etype*, customTypeCode>::dimensions, ERROR_THIS_OVERLOAD_IS_ONLY_FOR_ARRAYS);
		set(data, ConfirmAllowed<Etype*, customTypeCode>::typeName, ConfirmAllowed<Etype*, customTypeCode>::customTypeName, ConfirmAllowed<Etype*, customTypeCode>::dimensions, sizes, true);
	}
Wieso schmeißt mir Visual Studio da

Code: Alles auswählen

warning C4002: too many actual parameters for macro 'COMPILE_TIME_ASSERT_TRUE_MSG'
:?:

Bevor der cstomTypeCode als template-Parameter für ConfirmAllowed dazu kam, gabs dieses Warning nicht, dabei haben sich die Parameter seitdem doch gar nicht verändert, sondern sind weiterhin die erwarteten 2...
"Mir ist auch klar, dass der Tag, an dem ZFX und Developia zusammengehen werden der selbe Tag sein wird, an dem DirectGL rauskommt."
DirectGL, endlich ist es da
:)

"According to the C++ standard, it's "undefined". That's a technical term that means, in theory, anything can happen: the program can crash, or keep running but generate garbage results, or send Bjarne Stroustrup an e-mail saying how ugly you are and how funny your mother dresses you." :shock:[/size]
Benutzeravatar
BeRsErKeR
Establishment
Beiträge: 689
Registriert: 27.04.2002, 22:01

Re: initialize static data member in derived class

Beitrag von BeRsErKeR »

Ich vermute ja fast, dass der Präprozessor das Komma zwischen den Template-Parametern als Trennung für die Macro-Parameter interpretiert und daher von 3 Parametern ausgeht. Wieder ein schönes Beispiel, warum man solche Macro-Spielereien vermeiden sollte. ;)

Es ist halt nur eine Textersetzung. Nicht mehr und nicht weniger.
Ohne Input kein Output.
Benutzeravatar
Krishty
Establishment
Beiträge: 8268
Registriert: 26.02.2009, 11:18
Benutzertext: state is the enemy
Kontaktdaten:

Re: initialize static data member in derived class

Beitrag von Krishty »

Warum nicht static_assert()?
seziert Ace Combat, Driver, und S.T.A.L.K.E.R.   —   rendert Sterne
Benutzeravatar
BeRsErKeR
Establishment
Beiträge: 689
Registriert: 27.04.2002, 22:01

Re: initialize static data member in derived class

Beitrag von BeRsErKeR »

Krishty hat geschrieben:Warum nicht static_assert()?
Wenn ich raten müsste, dann wahrscheinlich weil sein Compiler (genau wie meiner) dies noch nicht unterstützt. :)
Ohne Input kein Output.
Benutzeravatar
dot
Establishment
Beiträge: 1734
Registriert: 06.03.2004, 18:10
Echter Name: Michael Kenzel
Kontaktdaten:

Re: initialize static data member in derived class

Beitrag von dot »

Code: Alles auswählen

template <bool b>
struct static_assert_t;

template <>
struct static_assert_t<true> {};

#define static_assert(a) (static_assert_t<a>())

...

static_assert(false);  // <- compilerfehler von wegen incomplete type
;)

EDIT: Ich sollte wohl mal anfangen ganze Threads zu lesen...
kaiserludi
Establishment
Beiträge: 467
Registriert: 18.04.2002, 15:31

Re: initialize static data member in derived class

Beitrag von kaiserludi »

BeRsErKeR hat geschrieben:Ich vermute ja fast, dass der Präprozessor das Komma zwischen den Template-Parametern als Trennung für die Macro-Parameter interpretiert und daher von 3 Parametern ausgeht. Wieder ein schönes Beispiel, warum man solche Macro-Spielereien vermeiden sollte. ;)

Es ist halt nur eine Textersetzung. Nicht mehr und nicht weniger.
Das könnte gut sein.
BeRsErKeR hat geschrieben:
Krishty hat geschrieben:Warum nicht static_assert()?
Wenn ich raten müsste, dann wahrscheinlich weil sein Compiler (genau wie meiner) dies noch nicht unterstützt. :)
Ja, Visual Studio unterstützt das erst ab Version 2010 und das Projekt muss noch unter VS 2008 kompilieren (haben erst vor einem Jahr VS 2005 Support fallen gelassen).
"Mir ist auch klar, dass der Tag, an dem ZFX und Developia zusammengehen werden der selbe Tag sein wird, an dem DirectGL rauskommt."
DirectGL, endlich ist es da
:)

"According to the C++ standard, it's "undefined". That's a technical term that means, in theory, anything can happen: the program can crash, or keep running but generate garbage results, or send Bjarne Stroustrup an e-mail saying how ugly you are and how funny your mother dresses you." :shock:[/size]
Benutzeravatar
BeRsErKeR
Establishment
Beiträge: 689
Registriert: 27.04.2002, 22:01

Re: initialize static data member in derived class

Beitrag von BeRsErKeR »

Versuchs mal so:

Code: Alles auswählen

COMPILE_TIME_ASSERT_TRUE_MSG((!ConfirmAllowed<Etype, customTypeCode>::dimensions), ERROR_THIS_OVERLOAD_IS_ONLY_FOR_SCALAR_TYPES);
Also mit zusätzlichen Klammern.
Ohne Input kein Output.
kaiserludi
Establishment
Beiträge: 467
Registriert: 18.04.2002, 15:31

Re: initialize static data member in derived class

Beitrag von kaiserludi »

BeRsErKeR hat geschrieben:Versuchs mal so:

Code: Alles auswählen

COMPILE_TIME_ASSERT_TRUE_MSG((!ConfirmAllowed<Etype, customTypeCode>::dimensions), ERROR_THIS_OVERLOAD_IS_ONLY_FOR_SCALAR_TYPES);
Also mit zusätzlichen Klammern.
Natürlich! Eigentlich naheliegend, das auszuprobieren. Funzt :)
"Mir ist auch klar, dass der Tag, an dem ZFX und Developia zusammengehen werden der selbe Tag sein wird, an dem DirectGL rauskommt."
DirectGL, endlich ist es da
:)

"According to the C++ standard, it's "undefined". That's a technical term that means, in theory, anything can happen: the program can crash, or keep running but generate garbage results, or send Bjarne Stroustrup an e-mail saying how ugly you are and how funny your mother dresses you." :shock:[/size]
Antworten