- 12V Akku mit 280 Ah bauen         
Ergebnis 1 bis 10 von 12

Thema: gemischter Vergleich mit signed und unsigned

Hybrid-Darstellung

Vorheriger Beitrag Vorheriger Beitrag   Nächster Beitrag Nächster Beitrag
  1. #1
    Erfahrener Benutzer Roboter Genie
    Registriert seit
    05.11.2007
    Beiträge
    1.076
    So, ich hoffe, ich habe es jetzt richtig verstanden. Eine Rückmeldung wär nett, "Jo, stimmt "oder "völliger Blödsinn"

    Ich versuche mal das Problem zu beschreiben, so wie ich es jetzt verstanden habe:

    Der Compiler möchte einen Vergleich zweier Zahlen durchführen.


    30.11.2011 Siro ist schlauer geworden......
    !!!!!! was jetzt folgt ist völliger Blödsinn und ich möchte nicht, daß Ihr nur annähernd glaubt was ich hier vorher interpretiert habe.
    Ich lasse es aber der Vollständigkeit halber trotzdem stehen
    .

    signed int a;
    unsigned int b;
    if (a < b) ...



    Wir stellen ihm einen signed int 32 Bit Wert zur Verfügung „a“
    . Das ist also ein 31 Bit Wert für die Zahlendarstellung und ein zusätzliches Bit für das Vorzeichen. Dann haben wir einen unsigned Wert „b“auch 32 Bits, dieser hat aber KEIN Vorzeichen, hier werden also alle 32 Bits für die Zahlendarstellung benötigt. Damit der Compiler einen Vergleich durchführen kann, versucht er zunächst beide Werte auf die gleiche Anzahl Bits zu „erweitern“. Da also Wert „b“ 32 Bits ohne Vorzeichen hat und Wert „a“ ein Vorzeichen besitzt, benötigen wir mindestens einen Datentyp mit 33 Bits. 32 Bits für die Zahlendarstellung und ein Bit für das Vorzeichen. Das geht aber nicht, da der Datentyp „int“ in meinem Falle mit 32 Bit schon voll ausgelastet ist. Was also tun ??? Man hat sich anscheinend mal dazu entschieden, das Vorzeichen wegzulassen, damit der 32 Bit Zahlenwert in den „int“ rein passt. Das Vorzeichen wird also nun für die eigentliche Zahlendarstellung benutzt und schwups wird aus einem signed int ein unsigned int. Was natürlich Auswirkungen auf das Ergebnis hat. Der Vergleich schlägt fehl. Entscheidend ist die interne Darstellungsweise des Datentyps „int“ und dieser ist je nach verwendeten Compiler bzw. verwendeter Zielhardware unterschiedlich. Kann also 8,16,32 oder sogar 64 Bit breit sein. Also kurz gesagt, der Compiler versucht den nächst „breiteren“ (grösseren) Datentyp zu wählen in den beide Werte komplett mit Vorzeichen hineinpassen. Bei meinem Prozessor mit „int“ = 32 Bit kann er also ohne Probleme und ohne Datenverlust einen unsigned short (16 Bit) in einen signed int (32) Bit wandeln, was er aber nicht kann, ist eine 32 Bit unsigned int ohne Datenverlust in einen int mit 32 Bit plus Vorzeichenbit wandeln. Also verschwindet das Vorzeichen und der Wert wird unweigerlich als unsigned interpretiert obwohl er eigentlich signed sein sollte.


    Siro.
    Geändert von Siro (30.11.2011 um 18:39 Uhr)

  2. #2
    Erfahrener Benutzer Roboter Experte Avatar von sternst
    Registriert seit
    07.07.2008
    Beiträge
    672
    Eine Rückmeldung wär nett, "Jo, stimmt "oder "völliger Blödsinn"
    Ich weiß gar nicht so recht, wo ich das jetzt einordnen soll. Das stimmt irgendwie alles so halb. Was allerdings überhaupt nicht stimmt, ist der Grund warum der Compiler aus den short für den Vergleich int macht. Mit den Vorzeichen und gemischten Vergleichen hat das nämlich nichts zu tun.
    MfG
    Stefan

  3. #3
    Erfahrener Benutzer Roboter Genie
    Registriert seit
    05.11.2007
    Beiträge
    1.076
    Schade eigentlich, für mich klang das sehr plausibel.
    Dann sollte ich den Text mal lieber wieder löschen, sonst glaubt das noch jemand so.
    Siro

  4. #4
    Moderator Robotik Visionär Avatar von radbruch
    Registriert seit
    27.12.2006
    Ort
    Stuttgart
    Alter
    62
    Beiträge
    5.799
    Blog-Einträge
    8
    Hallo

    Laß den Text mal besser stehen. Auch wenn's noch nicht stimmt würde der Thread durchs Löschen zu sehr zerrissen. Nettes Grundlagenthema finde ich übrigends.

    Gruß

    mic
    Bild hier  
    Atmel’s products are not intended, authorized, or warranted for use
    as components in applications intended to support or sustain life!

  5. #5
    Erfahrener Benutzer Roboter Experte Avatar von sternst
    Registriert seit
    07.07.2008
    Beiträge
    672
    Siro,
    du solltest dir wirklich mal ernsthaft Gedanken um dein grundsätzliches Vorgehen machen. Ständig probierst du nur rum und ziehst dann aus deinen Beobachtungen deine eigenen Schlüsse, wie es sein könnte. Man kann eine Programmiersprache auf die Art nicht richtig lernen. Zum einen können diese Schlüsse schlicht falsch sein (was sie ja auch schon mehrfach waren), zum anderen hat jede Sprache irgendwelche Grundregeln, die man sich fast unmöglich auf diese Art selbst "erarbeiten" kann. Und warum sollte man das auch überhaupt erst probieren, wo doch der richtige Weg nicht nur zuverlässiger, sondern auch schneller ist. In der Zeit, die du bisher mit deinen "Eigenforschungen" verbracht hast, hättest du mit Sicherheit auch locker ein C-Buch sorgfältig durcharbeiten können. "Herumprobieren" ist höchstens sinnvoll, um zu überprüfen, ob man alles richtig verstanden hat. Und wenn ich dann noch daran denke, dass es bei dir nicht um eine Freizeitbeschäftigung geht, sondern um deinen Job ....


    Zum Thema:

    '<' ist ein normaler Operator wie auch '+', '-', etc. Das bedeutet, dass für ihn auch die Integer-Promotion-Rules gelten. Im wesentlichen ist das:
    1) Die Typen der Operanden werden auf die selbe Größe gebracht. Der Größte "gibt den Takt vor", mindestens aber int.
    2) Haben die Typen bereits die selbe Größe, aber eine unterschiedliche Signedness, wird in unsigned gerechnet.

    Bei den int-Operanden sorgt 2) für das unerwartete Ergebnis.
    Bei den short-Operanden spielt 2) keine Rolle mehr, nachdem 1) angewendet wurde.
    MfG
    Stefan

  6. #6
    Erfahrener Benutzer Roboter Genie
    Registriert seit
    05.11.2007
    Beiträge
    1.076
    Naja, hättest ruhig sagen können, daß es ziemlicher Blödsinn ist, was ich geschrieben habe.
    So hätte ich es mir vielleicht gedacht, aber so funktioniert es nunmal nicht.
    Also ich versuche es noch einmal und werde jede Aussage separat halten, so könnt Ihr mir ein Sternchen vergeben wenn die Aussage richtig ist.
    Ich möchte es ja einfach nur verstehen.

    Der Standard Datentyp in "C" ist "int"

    Wie groß ein "int" ist, hängt vom System ab.

    Es können KEINE, weder logische noch mathematische Operation mit Werten durchgeführt werden, die eine kleinere Rangfolge haben als ein "int".

    Die Rangfolge entspricht dem Speicherbedarf. ??? mach ich mal 3 Fragezeichen, ist das so ???

    Aus einem char (8 Bit, unabhängig davon ob signed oder unsigned) wird vor einer logischen oder mathematischen Funktion ein "int"

    Aus einem short (16 Bit, unabhängig davon ob signed oder unsigned) wird vor einer logischen oder mathematischen Funktion ein "int"
    unter der Vorraussetzung, daß der Datentyp "short" eine geringere Rangfolge hat als der "int".

    Werden 2 "int" Werte in eine logische oder mathematische Operation verwickelt, wovon einer der beiden ein unsigned ist,
    wird der zweite Operand (der eigentlich signed ist) zu einem unsigned.

    Habe den Text übrigens vor deinem letzten Beitrag (von sternst) geschrieben. Hab mich den ganzen Tag mit bescchäftigt, sogar den Assembler Code zerpflückt.
    Danke nochmal.

    Korrektur 30.11.2011
    Stimmt irgendwie alles nicht, wie ich grad feststellen muste. Die Beschreibung lässt doch sehr zu wünschen übrig, wie die Integer Promotion funktioniert oder funktionieren sollte.
    Rechnen tut er "oftmals" richtig, aber vergleichen geht ständig schief. Das Verhalten wird immer merkwürdiger.......
    Hab auch keinen Bock mich weiterhin mit diesem Blödsinn auseinanderzusetzen, zumal mein Controller Vorzeichenrichtig in Hardware vergleichen kann, aber C baut einen derartigen Code herum, daß es nicht mehr funktioniert.
    In Assembler läuft es einwandfrei.

    Die einzige Möglichkeit welche ich gefunden habe, damit der C-Code wieder richtig funktioniert, ist die explizite Typwandlung vor dem Vergleich. Ansonsten ist das Ergebnis "UNDEFINIERT"
    bzw. Compiler (Prozessor) spezifisch, also:

    if (signed(a) > signed (b)) ......




    Siro
    Geändert von Siro (30.11.2011 um 18:48 Uhr)

  7. #7
    Erfahrener Benutzer Roboter Genie
    Registriert seit
    05.11.2007
    Beiträge
    1.076

    Ach Du meine Güte, da funktioniert ja garnichts

    geschlossen.
    Geändert von Siro (08.12.2011 um 15:24 Uhr)

Ähnliche Themen

  1. unsigned volatile long ??
    Von Ali_Baba im Forum C - Programmierung (GCC u.a.)
    Antworten: 9
    Letzter Beitrag: 04.03.2009, 20:31
  2. Warum uint16_t statt unsigned int?
    Von ricola im Forum C - Programmierung (GCC u.a.)
    Antworten: 6
    Letzter Beitrag: 05.07.2007, 17:38
  3. Signed integer-Werte Vergleichen
    Von *Mario* im Forum PIC Controller
    Antworten: 1
    Letzter Beitrag: 21.06.2006, 11:09
  4. 16Bit unsigned integer auf AVR
    Von cumi im Forum C - Programmierung (GCC u.a.)
    Antworten: 2
    Letzter Beitrag: 13.04.2006, 20:07
  5. Signed or Unsigned
    Von Arexx-Henk im Forum C - Programmierung (GCC u.a.)
    Antworten: 4
    Letzter Beitrag: 13.02.2006, 16:05

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • Anhänge hochladen: Nein
  • Beiträge bearbeiten: Nein
  •  

Solar Speicher und Akkus Tests