Frage zu struct in c

OP #7294513
Lesenswert?

Hi,

wenn ich das habe:

typedef struct
{
    uint32_t    day     : 5,
                month   : 4,
                year    :13,
                week    : 3,
                calweek : 6,
                leapjear: 1;
}date_t;

das mache:

date_t nav_date, act_date;

dann beide befülle mit Daten...

kann ich für einen Vergleich einfach das machen:

if (nav_date == act_date) ---

oder das, wenn ich alles aus act_date mav_date zuweisen möchte

nav_date=act_date;

Ist es so einfach?

Danke
DS
#7294520
Lesenswert?

Dennis S. schrieb:
> if (nav_date == act_date) ---

Wenn eine Struct Löcher enthält, ist deren Inhalt undefiniert. Der 
blockweise Vergleich ist somit ebenfalls undefiniert. Folglich lässt C 
einen Vergleich von Structs nicht zu.

Mit memcmp ginge es zwar technisch, und wird hier zumindest bei einem 
32-Bit Prozessor mangels Löchern üblicherweise funktionieren, hat aber 
vom Prinzip her das gleiche Problem.

> nav_date=act_date;

Das hingegen geht.
Gast #7294565
Lesenswert?

Thomas schrieb:
> Warum testest du das nicht einfach?
> Versuch macht kluch...

Es liefert Dir maximal einen Fehler. Weder Gewissheit wenn es 
funktioniert, noch einen workaround wenn nicht.

Beispiel hier: bei == meckert der Compiler. Also versucht er memcmp und 
das klappt.

Soll er dann annehmen, dass man structs mit memcmp vergleichen kann?
Gast #7294575
Lesenswert?

Strukturzuweisungen sind in C seit C90 zulässig.

Strukturvergleiche kennt C nicht, und Strukturen lassen sich ersatzweise 
nur dann sinnvoll mit memcmp vergleichen, wenn sie gepackt sind, d.h. 
Strukturelemente ohne Rücksicht auf Alignment angeordnet sind.

Andernfalls vergleicht memcmp auch ungenutzte Füllbytes, die reinstes 
Bitrauschen enthalten können. Und das ist nicht Ziel der Übung.
#7294578
Lesenswert?

Wenn Du, wie im Beispiel, wirklich jedes Bit definierst und auch 
vergleichen willst, könntest Du dir mit einer union abhelfen:

typedef union
{
    struct {
        uint32_t    day     : 5,
                    month   : 4,
                    year    :13,
                    week    : 3,
                    calweek : 6,
                    leapjear: 1;
    };
    uint32_t date;
} date_t;

Dann klappt der Vergleich mittels

if (nav_date.date == act_data.date)
#7294584
Lesenswert?

Klaus schrieb:
> Wenn Du, wie im Beispiel, wirklich jedes Bit definierst und auch
> vergleichen willst, könntest Du dir mit einer union abhelfen

Da Bitfelder ziemlich schwach definiert sind, ist das aber nicht 
garantiert. Vorsichtshalber sollte man dann auf sizeof(date_t)==4 
prüfen, um keine Überraschungen zu erleben. Einem Compiler eines 
16-Bitters könnte sauer aufstossen, dass year über einer 16-Bit Grenze 
liegt, mit Bitlöchern als Folge. In dem Fall würde eine dem angepasste 
Anordnung der Komponenten zu einem anderen Ergebnis führen.

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren