mehrere typenbezeichner für einen datentypen ohne mehrdeutigkeiten



  • hihooo leute hoffe das das keine dämliche frage ist ^^

    ich hatte aus konsistenz gründen vor für in meinen klassen verwendeten datentypen jeweils aliase zu erzeugen. mittels typedef war mein erster gedanke nur hat mein compiler mich wieder mal drauf aufmerksam gemacht das er die ^^ umbenennungen ja später unbemerkt macht. das ist echtn bissl doof weil ich eintlich ein paar member-fkt überladen wollte und nur anahnd des datentyps entscheiden lassen wollte.

    class Test
    {
    
    public:
    	typedef int 		IdType;
    	typedef wxDateTime 	DateType;
    	typedef wxString 	NameType;
    	typedef wxString 	LocoType;
    	typedef wxString 	LocaType;
    	typedef wxString 	FormatIdType;
    	typedef wxString 	FormatDateType;
    
    public:
    	static FormatIdType		Format(IdType id2format);
    	static FormatDateType		Format(DateType date2format);
    	static IdType			Format(FormatIdType formatId2format);
    	static DateType			Format(FormatDateType formatDate2format);
    
    public:
    	static bool	IsValid(IdType id2validate);
    	static bool	IsValid(DateType date2validate);
    	static bool	IsValid(FormatIdType formatId2validate);
    	static bool	IsValid(FormatDateType formatDate2validate);
    
    };
    

    najaaaaa 😕 das das nicht läuft war ja klar. nun hatte ich noch versucht mit klassen neudeklarationen zu handeln. allerdings hab ich dann ja wieder bei den primitiven datentypen probleme... hat iwer ne ideee dafür? entweder ne einfache wrapper<...> klasse oder iwas anderes ^^ noch simpleres?

    class Test
    {
    
    public:
    	class IdType 	: public int {}; // das geht ja leider net
    	class IdType 	: public Wrapper<int> {}; // das wär ok
    	class DateType 	: public wxDateTime {};
    	calss NameType 	: public wxString {};
    ....
    
    };
    

    ja also das mit dem wrapper hab ich probiert aber als ich dann jeden gültigen operator neu schreiben musste 😕 dacht ich es muss doch noch was einfacheres geben....



  • In wiefern unterscheiden sich denn die Aufrufe der Funktion? Ich würde mir da sonst überlegen, dass du das mit einem enum erledigen könntest.

    enum {NameType, LocoType ...};
    

    Und dann einfach beim Funktionsaufruf mitangeben und darauf reagieren.



  • isaias schrieb:

    ja also das mit dem wrapper hab ich probiert aber als ich dann jeden gültigen operator neu schreiben musste

    wozu? willst du IdKlassen addieren, dividieren, oder sonst etwas? die einzige operation, die du brauchst, ist anscheinend IsValid. mehr lässt sich aus deinem code heraus nicht sagen.



  • Naja, wenn sich wirklich fachlich unterschiedliche daten dahinter verbergen, kannst Du die Typen auch wrappen:

    struct NameType {   wxString value; };
    struct LocoType {   wxString value; };
    struct LocaType {   wxString value; };
    ...
    

    Ich weiß nicht, ob das Dein Problem löst, aber immerhin bekommst Du damit unterschiedliche Klassen und kannst Gebrauch von overloading und templates machen.

    Gruß,

    Simon2.



  • drakon schrieb:

    In wiefern unterscheiden sich denn die Aufrufe der Funktion? Ich würde mir da sonst überlegen, dass du das mit einem enum erledigen könntest.

    enum {NameType, LocoType ...};
    

    Und dann einfach beim Funktionsaufruf mitangeben und darauf reagieren.

    neee also der aufruf sollte ja schon transparent laufen, ich möchte schon das der compiler erkennt welche methode aufzurufen ist,

    wenn iwo eine derartige zeile auftaucht

    Test::IdType id;
    
    if(Test::IsValid(id))
    {
        Test t;
        t.Id(id); // dieses iss der normale setter für das private member Test::IdType id;
        ....
    }
    
    // analog soll aber auch folgendes gehen, also ^^ da ich faul bin wollt ich mir das
    // explizite trennen mittels enum sparen sry aber danke ;)
    
    Test::LocaType location;
    
    if(Test::IsValid(location))
    {
        Test t;
        t.Loca(location);
    }
    

    queer_boy schrieb:

    isaias schrieb:

    ja also das mit dem wrapper hab ich probiert aber als ich dann jeden gültigen operator neu schreiben musste

    wozu? willst du IdKlassen addieren, dividieren, oder sonst etwas? die einzige operation, die du brauchst, ist anscheinend IsValid. mehr lässt sich aus deinem code heraus nicht sagen.

    also innerhalb der klasse werden ja mit der id berechnungen angefertigt... der prozess um eine neue id zu ermitteln bspw da brauch ichs dereferenzieren addieren und nja das wärs schoooo, aber ich dacht ich beschränk ^^ meine frage mal aufs wesentliche....

    Simon2 schrieb:

    Naja, wenn sich wirklich fachlich unterschiedliche daten dahinter verbergen, kannst Du die Typen auch wrappen:

    struct NameType {   wxString value; };
    struct LocoType {   wxString value; };
    struct LocaType {   wxString value; };
    ...
    

    Ich weiß nicht, ob das Dein Problem löst, aber immerhin bekommst Du damit unterschiedliche Klassen und kannst Gebrauch von overloading und templates machen.

    Gruß,

    Simon2.

    alsooo die letzte variante scheint mir noch am sinnigsten aber.... 😕
    ich hatte nicht vor immer noch auf das gewrappte element zuzugreifen habe schon
    konvertierungs operatoren und hoffe ich passende konstruktoren gebastelt gehabt aber
    ich konnte nicht wirklich transparent mit dem wrapper arbeiten evtl hab ich da ja einen denkfehler drin
    ich hab ^^ den entwurf wieder verworfen aber ich rekonstruier des mal

    template<typename T>
    struct Wrapper
    {
    	T val;
    	Wrapper(const T & val_) : val(val) {}
    	Wrapper(const Wrapper & wrapper) : val(wrapper.val) {}
    	operator T () { return val; }
    };
    

    in der klasse würden die definitionen dann bei einem primitiven datentypen so ausschauen

    class Test
    {
        struct IdType : public Wrapper<int> {};
        struct DateType : public wxDateTime {};
    ....
    };
    

    iwo in der source könnt das dann so aussehen

    Test::IdType a;
    Test t;
    
    t.Id(a+1);
    

    ist klar das er keinen operator+ für const Test as lhs arg und int as rhs arg hat
    was wenn ich es aber gern so schreiben würd ^^??? gibt es neben der expliziten konvertierung nicht auch
    die möglichkeit explizit implizite konvertierung zu erzeugen???? 😃
    alsoooo das a+1 in (int)a+1 umgewandelt würde ich mein der konvertierungsoperator ist ja daaaa ^^
    und dann wäre operator+(int, int) jaaa auch kein prob mehr.... aber das wär zuviel des guten nehm ich mal an

    öhm ich glaub ich werd wohl einfacha lle operatoren nochmal generisch durch deklarieren müssen oder??
    so viele sinds ja adnn auch net...

    besten dank für eure hilfe... 🙂 werd mal sehen wie ichs mach entweder zieh ich dsa soooo durch ^^ oder überleg mir doch noch was anderes.....



  • isaias schrieb:

    ...

    template<typename T>
    struct Wrapper
    {
    	T val;
    	Wrapper(const T & val_) : val(val) {}
    	Wrapper(const Wrapper & wrapper) : val(wrapper.val) {}
    	operator T () { return val; }
    };
    

    ...

    Also mit DEM Ansatz wirst Du vermutlich in Schwulitäten kommen, wenn Du mit Referenzen arbeiten willst ....
    Ich denke, Du musst Dich entscheiden: Entweder willst Du separate Typen haben (dann sind sie aber eben auch in ALLEN Belangen separat) oder nicht (dann sind sie es nie).

    Gruß,

    Simon2.



  • function overloading? ^^ drauf gesch***

    alsooo hab wie du schon gesagt hast nur die 2 möglichkeiten gehabt.... gefiel mir beides nicht....
    der konsistenteste weg ist doch..... den fkt-namen anzupassen gewesen
    vor allem wenn es jetzt wächst

    der wrapper hats zwar getan ... aber es war nicht wirklich hübsch..... 😃 😃 😃 nun gut
    danke für die viele hilfe

    lg isaias



  • isaias schrieb:

    ...
    der konsistenteste weg ist doch..... den fkt-namen anzupassen gewesen
    ...

    Was meinst Du mit "Funktionsnamen anpassen" ?
    und vielleicht könntest Du "nicht gefallen" ein wenig näher spezifizieren: In welcher Situation entstehen dadurch Schwierigkeiten ?
    Man kann Dir so schlecht helfen, wenn Du nur Dein subjektives Ästhetikempfinden als Kriterium nimmst... 😉

    Gruß,

    Simon2.


Anmelden zum Antworten