www.mikrocontroller.net

Forum: Compiler & IDEs unsigned - unsigned = signed?!


Autor: mC (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Servus Forum,

ich steh grad bissl aufm Schlauch. Folgender Ausschnitt aus meinem 
C-Code:
uint8_t i;
uint8_t j;
int8_t k;

...

k = i - j;
i ist nicht zwangshalber größer als j, wird mein k trotzdem richtig 
berechnet? ich steh bissl aufm Schlauch. eigenlich wird ja mein Ergebnis 
erst unsigned berechnet und dann erst in einen signed integer 
umgewandelt, was mir Fehler bei i<j liefern sollte oder nicht?
Oder wird mir k in einem Wertebereich von -128 bis 127 immer korrekt 
ausgerechnet?


PS: ich hab die suche verwendet, aber ich weiß nciht so genau nach 
welchen stichworten ich suchen soll und so ist meine suche recht 
erfolglos geblieben

Autor: Benedikt K. (benedikt) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
mC schrieb:
> i ist nicht zwangshalber größer als j, wird mein k trotzdem richtig
> berechnet?

Ja, dank Zweierkomplement.

> eigenlich wird ja mein Ergebnis
> erst unsigned berechnet und dann erst in einen signed integer
> umgewandelt,

Ja.
Warum es aber dennoch funktioniert liegt wie oben schon geschrieben am 
Zweierkomplement: 5 - 10 = -5, oder wenn bei 8bit unsigned Zahlen 
bleibt: 5-10+256=251

251 im Zweierkomplement betrachtet (was die signed Zahlen machen), 
entspricht -5. Das Ergebnis passt also.

Daher ist es bei Addition und Subtraktion egal, ob man erst rechnet oder 
umwandelt wenn das Zweierkomplement verwendet wird, nur bei 
Multiplikation und Division muss man aufpassen.

Autor: Thomas B. (yahp) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
> Daher ist es bei Addition und Subtraktion egal...

Halt! Natürlich ist es hier nicht egal. Aufgrund des unterschiedlichen 
Wertebereiches kann es hier schon zu Bereichsüberläufen kommen.

Bsp: i=255, j=1, k=???

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Thomas B. schrieb:

> Halt! Natürlich ist es hier nicht egal. Aufgrund des unterschiedlichen
> Wertebereiches kann es hier schon zu Bereichsüberläufen kommen.

Es muss tatsächlich nicht immer das gleiche wie bei vorzeichenbehafteter 
Rechnung rauskommen, weil das Verhalten von vorzeichenbehafteter 
Rechnung bei Überlauf undefiniert ist.

Solange man aber vorzeichenlos rechnet und die Maschine mit 
Zweierkomplement arbeitet wird da nichts anbrennen. Andersrum kann das 
aber in die Hose gehen, vor allem bei der Multiplikation, weil da zwar 
das Produkt (dessen in C einzig relevante untere Hälfte) neutral ist, 
aber der Compiler bei vorzeichenbehafteter Rechnung Abkürzungen nehmen 
darf, die zu einem bei Überlauf nicht mehr korrekten Ergebnis führen 
können. Bei Add/Sub ist das weniger wahrscheinlich.

Autor: Benedikt K. (benedikt) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Thomas B. schrieb:
>> Daher ist es bei Addition und Subtraktion egal...
>
> Halt! Natürlich ist es hier nicht egal. Aufgrund des unterschiedlichen
> Wertebereiches kann es hier schon zu Bereichsüberläufen kommen.
>
> Bsp: i=255, j=1, k=???

Nur funktioniert dieses Beispiel genausowenig mit 8bit signed Zahlen...

Autor: der mechatroniker (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Allerdings sagt der C-Standard meines Wissens weder, dass mit 
Zweierkomplement gerechnet wird, noch dass dann mit Zweierkomplement 
gerechnet wird, wenn die Zielplattform das nativ tut (mal vom Sinn 
abweichender Implementierungen abgesehen).

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
der mechatroniker schrieb:

> Allerdings sagt der C-Standard meines Wissens weder, dass mit
> Zweierkomplement gerechnet wird

Da liegt du zwar richtig, aber Seymour Cray ist längst tot und sein 
geliebtes Einerkomplement starb in ganzzahliger Rechnung schon vorher 
(*). Insofern muss man an dieser Front wohl nicht päbstlicher sein als 
der Pabst.

Von der TCP/IP-Checksum mal abgesehen.

Autor: Benedikt K. (benedikt) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
der mechatroniker schrieb:
> Allerdings sagt der C-Standard meines Wissens weder,

Stimmt auch wieder. Wenn man den Code also wirklich universell schreibt, 
sollte man dies beachten. Allerdings ist mir nur noch ein Compiler 
untergekommen, der nicht mit Zweierkomplement gerechnet hätte.

Autor: Thomas B. (yahp) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
>> Bsp: i=255, j=1, k=???
>Nur funktioniert dieses Beispiel genausowenig mit 8bit signed Zahlen...

Freilich nicht, aber dort kommt es halt auch gar nicht vor!

Autor: Nn Nn (jaytharevo)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
uint16_t OCR1A_tmp = 0, OCR1B_tmp = 0;
 int16_t delta_th = 0, delta_el = 0;

.
.
.
.

delta_el = OCR1A - OCR1A_tmp;
delta_th = OCR1B - OCR1B_tmp;

OCR1A = OCR1A - delta_el/100;
OCR1B = OCR1B - delta_th/100;

Hey!

Könnte diese Rechnung theoretisch passen?

Controller ist ein ATMEGA88PA.

MfG,
Julian

Edit: Frohe Weihnachten :)!

Autor: Herr Duden (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@A.K. (prx)

Kleiner, aber freundlich gemeinter Offtopic-Hinweis vom Duden-Team: Es 
heißt "Papst" und dementsprechend auch "päpstlich". Das Wort Kommt vom 
lateinischen "papa" = Vater.

Autor: Tom (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Herr Duden, kleiner aber freundlich gemeinter Hinweis: Der Thread ist 
ca. 13 Monate alt!

Autor: Klaus Wachtler (mfgkw)
Datum:
Angehängte Dateien:

Bewertung
0 lesenswert
nicht lesenswert
Kommt drauf an, wie er den Satz verstanden haben möchte.
Wenn er meint, man müsse nicht mehr unnötigen Wind machen, als ein
solider Lüfter, dann ist es richtig geschrieben :-)

Abgesehen davon, daß es wohl vielleicht aus dem Griechischen kommt.
Meint zumindest Meyers Konversationslexikon.

Autor: Nn Nn (jaytharevo)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Wie wärs wenn jemand mal meine Frage liest^^ xD!

Autor: Rolf Magnus (rmagnus)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Der Papst weiß doch alles, oder? Dann kannst du doch den mal fragen. ;-)
Aber mal im Ernst: Warum hängst du deine Frage eigentlich an einen 
Uralt-Thread an?
Und nun noch zur Frage:

> Könnte diese Rechnung theoretisch passen?

Hmm, könnte sie theoretisch, abhängig davon, was sie tun soll. Was steht 
denn in OCR1A_tmp drin? Ist es gewünscht, daß ein negativer Wert 
rauskommt, wenn die Differenz zwischen OCR1A und OCR1A_tmp sehr groß 
ist? Warum ist das delta vorzeichenbehaftet?

Autor: A. K. (prx)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Julian Schild schrieb:

> Wie wärs wenn jemand mal meine Frage liest^^ xD!

Tja, und dann? Die _tmp Dinger sind bei dir 0 und die Deltas sind daher 
identisch mit den OCRs. Die werden folglich schrumpfen bis sie unter 100 
sind. Von da an ändert sich nix mehr.

Sollten die tmps mal nicht 0 sein: Die Sache hängt beispielsweise ein 
bisserl davon ab, wie weit der Zähler zählt. Muss ja nicht 0xFFFF sein.

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.