das problem mit den padding bytes



  • Original erstellt von Dimah:
    *würde aber auf die gleichen casts hinauslaufen, es würde einen den vorteil bringen das man sicher wäre das die referenzen nicht die größe der stuct verändern und dann kännte man so was machen stream.read( static_cast<void >( &foo ), sizeof( foo ) );
    aber das kann man sowieso so nicht machen, da das array auch gepaddet sein

    das würd ich in den konstruktor verlagern, und der kann dann die adresse von dem char array nehmen.
    aber so geht ja die ganze abstraktion verloren...
    sieht nix mehr nach gut C++ aus



  • Original erstellt von japro:
    ich glaube kaum das arrays gepaddet sein. bin jedenfalls immer davon ausgegangen das das nicht der fall ist.

    ich meine das struct foo { char a[3]; }; sizeof( foo ) == 4 sein könnte,

    Original erstellt von japro:
    **edit: könnte man da eigentlich nicht was mit mit templates und so machen (typlist etc.) bin momentan zu müde um mir selbst was zu überlegen...
    **

    ja nur würden die member dan sowas wie mem01, mem02 usw. heissen statt crc32 und size

    @davie jup, nur das mit den ctor kapiere ich nicht



  • statt

    fileheader x(file); //mach das alles in x's konstruktor
    

    machst du

    fileheader x;
    file.read (reinterpret_cast<unsigned char*>(&x), sizeof(x));
    

    OK, :), wer's mag... kannst du mit C aber auch machen.

    wenn du spaß dran hast (😕 ) dann kannst du ja auch deine const referenzen behalten. aber ob

    x.version () oder x.version ist in meinen augen ziemlich egal (von Kapselung abgesehen)

    oder bezweckst du irgendetwas, das mir entgangen ist 😕 ?



  • Original erstellt von davie:
    **statt

    fileheader x(file); //mach das alles in x's konstruktor
    

    machst du

    fileheader x;
    file.read (reinterpret_cast<unsigned char*>(&x), sizeof(x));
    

    OK, :), wer's mag... kannst du mit C aber auch machen.
    **

    was mir daran nicht gefält ist das ich dann abhänig mache von den stl streams, dieser ganze "definiert struct und lese binär ein" weg ist ja dazu da um das letzte quendchen speed raus zu hollen und viele stl stream implementierung würden den gewinn zu nichte machen

    Original erstellt von davie:
    **wenn du spaß dran hast (😕 ) dann kannst du ja auch deine const referenzen behalten. aber ob

    x.version () oder x.version ist in meinen augen ziemlich egal (von Kapselung abgesehen)

    oder bezweckst du irgendetwas, das mir entgangen ist 😕 ?**

    also in den stucts soll ja keine großartige logic hinein, sie sollen mir nur helfen die daten leichter rauszuhollen deswegen finde ich es auch nicht schimm public members zu haben, wenn ich logic hinein bringen will dann kann ich eine klasse um das teil bauen



  • wenn du's unbedingt so low level haben willst, wieso nicht einfach für die struct:

    struct foo {
      char buf[7]; //oder was auch immer
    /* den rest lass ich mal weg */
    };
    
    //...
    
    file.read (foo.buf, 7);
    

    geht doch auch? ob &foo oder foo.buf? ist doch fast das selbe...
    oder überlad dir den adress operator...

    char * operator & () { return buf; }
    

    und du ersparst dir sogar den lästigen reinterpret_cast.

    oder mach dir gleich nen operator char * () dann ersparst du dir sogar das &
    😃 😉



  • ahso, das meins du, ja baue ich ein, nur nenne ich sie data() (in anlehnung an std::string::data())



  • hu, du hast ja gleich geantwortet... bist du die etwa ganze zeit online?
    naja, wie dem auch ist, was meintest du denn, was ich meine?



  • file_header()
            :    version( *reinterpret_cast<unsigned char *>( buffer ) ),
                 file_size( *reinterpret_cast<unsigned long *>( buffer + 1 ) ),
                 crc16( *reinterpret_cast<unsigned short*>( buffer + 5 ) )
    

    das ist (mal von reinterpret_cast abgesehen) nicht portabel, da u.U. die Alignment-Forderungen der Typen unsigned long und unsigned short verletzt werden. Wenn man eine Architektur hat, an der DWords nur an durch 4 teilbaren Adressen liegen dürfen (alpha z.B. AFAIK), würde die Zuweisung an file_size crashen (davon abgesehen dass long auf der alpha 8 bytes groß ist, AFAIK, aber das Prinzip sollte klar sein).

    Ich würde es mit #ifdef systemabhängig machen, und im #else-Zweig als Fall-Through die absolut portable Fassung verwenden. Dadurch hast du beides: Geschwindigkeit in den meisten, und Sicherheit auch in obskuren Fällen.



  • Original erstellt von davie:
    hu, du hast ja gleich geantwortet... bist du die etwa ganze zeit online?
    naja, wie dem auch ist, was meintest du denn, was ich meine?

    dache ich habe in deinen vorherigen posting was übersehen, aber beim zweiten lesen fiel mir auf das es eine neue idee war

    Original erstellt von Bashar:
    Ich würde es mit #ifdef systemabhängig machen, und im #else-Zweig als Fall-Through die absolut portable Fassung verwenden. Dadurch hast du beides: Geschwindigkeit in den meisten, und Sicherheit auch in obskuren Fällen.

    jup wird mir wohl nix anders übrig bleiben, ich werds mal aber erst mit policen probieren aus zwei gründen, ich mag #if nicht und ich hatte bis her noch keine idee wo ich policen einsetzen kann



  • Policies ändern im Endeffekt aber nichts daran, dass du

    #if
    Foo<PackedPolicy> ...
    #else
    Foo<PortablePolicy>
    #endif

    schreiben mußt 😉


Anmelden zum Antworten