Forum: Mikrocontroller und Digitale Elektronik MSP430- Auslesen von Kommazahlen ?


von Wolfgang (Gast)


Lesenswert?

Da ich in den Anleitungen zu IAR und dem dazugehörigen C-Compiler nur
wenig zur Multiplikation mit Gleitkommazahlen gefunden habe bzw. auch
nicht alles verstanden habe, muss ich mal die Experten fragen.
Folgendes Problem:
Nach einer A/D Wandlung steht  im ADC12MEM0 Register eine 16(12) Bit
zahl.
a) Diese Zahl soll mit z.B. mit 3,76 multipliziert werden, dann
gerundet (damit wieder  ein ganzzahliger Wert entsteht) und dann
byteweise parallel an z. B. an P4 ausgegeben werden.
b) Wie kann man den vor der Rundung entstandenen Gleitkommawert
byteweise parallel an P4 ausgeben ?
Hat jemand zu meinen Problemen evtl. Programmschnipsel (vorzugsweise in
`C’ und mit viel Kommentar) ?
MfG
Wolfgang

von A.K. (Gast)


Lesenswert?

Sowas rechnet man nur dann mit Fliesskomma-Arithmetik, wenn man
unbedingt das Flash mit der entsprechenden Library vollkriegen will.

Ansonsten mit 376 multiplizieren, durch 100 dividieren und abhängig vom
Rest runden. Das 32bit Zwischenergebnis auszugeben sollte kein Problem
sein.

von Michael B. (Gast)


Lesenswert?

Vor der Division nicht vergessen 50 zu addieren und die Division rundet
automatisch richtig.

von Peter D. (peda)


Lesenswert?

Noch schneller und codesparender ist:

(X * 963 + 128) / 256


Peter

von Wolfgang (Gast)


Lesenswert?

Dank an alle. Leider bin ich noch nicht viel schlauer geworden, da meine
Programmierkenntnisse noch zu unvollkommen sind.
@ A.K. , wenn ich x*376/ 100 rechne, kommt bei mir wieder eine
Gleitkommazahl heraus, die ich, ohne auf einen ganzahligen Wert zu
runden, m.E. nicht an P4 ausgeben kann. Wo mache ich einen Denkfehler?

Wie kann ich runden ? gibt es eine Funktion dazu?
<Das 32bit Zwischenergebnis auszugeben sollte kein Problem sein.>
für mich ist es ein Problem, sonst würde ich nicht danach fragen.
wie wird z.B. das Komma ausgegeben? Oder wie muss ich mir das
vorstellen?
@ Peter, wie kommt man auf die von Dir vorgeschlagenen Zahlen?
< Noch schneller und codesparender ist:> für mich nicht so wichtig, da
ich noch nicht mal die langsamen Methoden kenne.

Vielleicht hat doch jemand ein Programmschnipsel mit Erläuterungen

MfG
Wolfgang

von Rufus T. Firefly (Gast)


Lesenswert?

Kleine Tips:

963 = 256 * 3,76
128 = 256 * 0,5

Multiplikation mit Zweierpotenzen ist einfach und schnell durch
Schiebebefehle zu realisieren.

von A.K. (Gast)


Lesenswert?

"wenn ich x*376/ 100 rechne, kommt bei mir wieder eine
Gleitkommazahl heraus"

Nur wenn Du den Taschenrechner nimmst. Nicht wenn Du das den
Micocontroller in ganzzahliger Rechung machen lässt. Aber Peter hat
hatürlich recht, durch 2er-Potenz zu dividieren ist noch simpler.

376/100 = 963/256.

Und die Rundung ergibt sich, indem vorher die Hälfte noch drauf addiert
und bei der ganzzahligen Division (bzw. der Schiebeoperation)
abgeschnitten, d.h. der Rest ignoriert wird.

von Wolfgang (Gast)


Lesenswert?

Nun hab ich es begriffen. Aber jetzt tritt ein neues Problem auf:
Wenn ich mit dem µC rechne U1= ADC12MEM0*963;
         U2 = U1+128;
         U3=U2 >> 8;     // Division  / 256
wobei die Variablen U1,U2,U3 als unsigned long deklariert worden,
wird das obere Byte vom 16Bit Endergebnis zu Null.
Kann es sein, dass die Demoversion von IAR Kickstart V.2.21B mit dem
Compiler V 2.21.2.2 unsigned long (32Bit) nicht kennt?
Muß noch eine *.h-Datei einbezogen werden ?
Was mache ich falsch?
MfG
Wolfgang

von Andreas (Gast)


Lesenswert?

Habe das selbe Problem auch mit meinem IAR Compiler (Renesas H8).
Möchte einen Wert von 90000 in eine unsigned Long Variable schreiben,
aber es wird nur 33464 angenommen. Bei einem älteren Projekt konnte ich
das Problem mit einer erzwungenen Typenumwandlung:
- (unsigned long)U2 = (unsigned long)U1+128
beheben können.

Bei meinem erneuten Problem komme ich aber auch damit nicht weiter.
Hoffe Dir damit geholfen zu haben und wäre sehr froh, wenn jemand ein
Typ hat für mein aktuelles Problem.

Danke

von Rufus T. Firefly (Gast)


Lesenswert?

.

  "Möchte einen Wert von 90000 in eine unsigned Long Variable
  schreiben, aber es wird nur 33464."

Ist sizeof (long) == 4?

Wenn ja, dann hilft das hintanstellen eines großen 'L' an die
Konstante:

  unsigned long wert = 90000L;

Die Konstante ist sonst nämlich eine int-Konstante ...

von Andreas (Gast)


Lesenswert?

Danke für Deine rasche Antwort!

Der Wert 90000 ist leider keine Konstante, sondern eine Variable,
welche im Programm verändert wird.
Die Funktion sizeof liefert mir auch den korrekten Wert 4.

Habe ein kleines Testprogramm geschrieben in dem alles problemlos
läuft. Es liegt also nicht grundsätzlich am IAR Compiler.

Für einen weiteren Typ bin ich sehr dankbar.

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.