www.mikrocontroller.net

Forum: Compiler & IDEs Brauche Hilfe beim Verstehen einer C-Zeile


Autor: FrageMan (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,

ich habe in einer .h Datei folgende Definition gesehen, und da diese 
Q15(X) in einem Beispiel Code verwendet wird, möchte ich verstehen, was 
diese Funktion eigentlich macht. Könnt mir bitte jemand helfen?

#define Q15(X) \
   ((X < 0.0) ? (int)(32768*(X) - 0.5) : (int)(32767*(X) + 0.5))

Autor: schuppi (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
if(X < 0.0)  (int)(32768*(X) - 0.5);
else         (int)(32767*(X) + 0.5);

jaja so ist das

Autor: Μαtthias W. (matthias) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hi

Umwandlung einer float Zahl in (bitof(int) - 15).15 Fixpointformat?

Matthias

Autor: Sven P. (haku) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
schuppi wrote:
> if(X < 0.0)  (int)(32768*(X) - 0.5);
> else         (int)(32767*(X) + 0.5);
>
> jaja so ist das

Blödsinn.
#define Q15(X) \
   ((X < 0.0) ? (int)(32768*(X) - 0.5) : (int)(32767*(X) + 0.5))

"\" setzt die Definition in der nächsten Zeile fort.
Da steht ein bedingter Ausdruck:
(
  (X < 0.0) ?                   /* WENN X < 0.0 */
  (int) (32768 * (X) - 0.5) :   /* DANN nimm diesen Ausdruck */
  (int) (32767 * (X) + 0.5)     /* SONST diesen hier. */
)

Der Ausdruck selbst:
  (int) (32768 * (X) - 0.5)
multipliziert die Kommazahl "X" (vermutlich Kommazahl, weil ja auch mit 
"0.0" verglichen wird) mit 32768 (macht sie quasi wortbreit, =2^15), 
zieht von dem Ergebnis ein Halb ab und verwirft danach die Kommastellen.

Ansonsten: Jo, das sieht nach Umwandlung in Festkommazahl aus.

Autor: Lothar Miller (lkmiller) (Moderator) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@ Sven Pauli (haku)
Ich kann mir nicht helfen, aber das
> if(X < 0.0)  (int)(32768*(X) - 0.5);
> else         (int)(32767*(X) + 0.5);

ist für mich das selbe wie das:
>  (X < 0.0) ?                   /* WENN X < 0.0 */
>  (int) (32768 * (X) - 0.5) :   /* DANN nimm diesen Ausdruck */
>  (int) (32767 * (X) + 0.5)     /* SONST diesen hier. */

Weshalb also
> Blödsinn.
??

Autor: Sven P. (haku) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Lothar Miller wrote:
> @ Sven Pauli (haku)
> Ich kann mir nicht helfen, aber das
>> if(X < 0.0)  (int)(32768*(X) - 0.5);
>> else         (int)(32767*(X) + 0.5);
>
> ist für mich das selbe wie das:
>>  (X < 0.0) ?                   /* WENN X < 0.0 */
>>  (int) (32768 * (X) - 0.5) :   /* DANN nimm diesen Ausdruck */
>>  (int) (32767 * (X) + 0.5)     /* SONST diesen hier. */
>
> Weshalb also
>> Blödsinn.
> ??

Weils Blödsinn ist. Deine IF-Version wird dem bedingten Ausdruck mit 
seinem beabsichtigten Einsatzzweck NICHT gerecht. Denk mal nach:
Welche Effekte hat
(int)(32768*(X) - 0.5)
eigentlich? Richtig -- garkeine. Da wird ein wenig rumgerechnet und 
danach ist alles so wie vorher.

Deine IF-Konstruktion wird so vom Kompiler schlicht wegoptimiert, und 
das zu Recht, weil sie effektiv nichts bewirkt.
Ganz anders dagegen der bedingte Ausdruck: der bewirkt zwar selbst auch 
nichts, aber man kann mit ihm weiterrechnen:

Bedingter Ausdruck:
#define Q15(X) \
  ((X < 0.0) ? (int) (32768 * (X) - 0.5) : (int) (32767 * (X) + 0.5))

if (Q15(...) == ...) {}
/* oder */
variable = Q15(...);

/* funktioniert */

Dein IF-Dings:
#define Q15(X) \
  if(X < 0.0)  (int)(32768*(X) - 0.5); else (int)(32767*(X) + 0.5);

if (Q15(...) == ...) {} /* Syntaxfehler */
variable = Q15(...); /* Syntaxfehler */


Das If-Ding müsstest du so formulieren:
#define Q15(X, Y) \
  if(X < 0.0)  \
    Y = (int)(32768*(X) - 0.5); \
  else \
    Y = (int)(32767*(X) + 0.5);

/* Damit wäre zumindest sowas möglich: */
Q15(..., variable);

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.