www.mikrocontroller.net

Forum: Compiler & IDEs Double Werte übergeben


Autor: loki81 (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hey,

Ich versuche gerade wieder einmal werte meines ADW an ein Display zu 
übergeben. So wqeit klappt auch alles nur die Berechnung de Spannung 
will nicht so ganz. Ich denke es liegt irgendwie an den Variablen Typen 
hoffe ich....

Ich habe folgendes:

int AD_WERT;
double ADCOUT;

ADCOUT = (5*AD_WERT/1023);
lcd_putd(ADCOUT);

Wenn ich "lcd_putd(234.567)" aufrufe geht es einwandfrei.
Wenn ich "ADCOUT = (5*515/1023)" aufrufe geht es nicht und ich bekomme 
nur die Anzeige 2.000V.

Hat jemand nen Tipp für mich?

loki

Autor: Jemand anderes (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ersetze mal
ADCOUT = (5*AD_WERT/1023);
durch
ADCOUT = (5.0*AD_WERT/1023.0);

Im ersten Falle wird eine Integermultiplikation und -Division 
durchgeführt, und erst das Ergebnis zu einem double konvertiert.
Das sieht in der anderen Version anders aus.

Autor: Εrnst B✶ (ernst)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Und wenn du eh schon am Ändern bist, ersetze 1023.0 durch 1024.0, dann 
stimmt dein Ergebnis sogar noch.

Autor: loki81 (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@all
Lieben Dank zusammen....

Hab das so geändert und siehe da es funst. Naja jedenfalls halb.

Double is immer signed oder? denn bis 565 alles super nur dann fängt 
meine Ausgabe wieder bei 0 an und zählt hoch.... Aber kommt Zeit kommt 
rat.

loki

Autor: Rufus Τ. Firefly (rufus) (Moderator) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
> Double is immer signed oder?

Double ist ein floating-Point-Format.

Autor: loki81 (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hey ich noch mal....

Ich hab immer noch probleme und keinen Durchblick wo ich anfangen soll 
was nachzulesen.....

Also wie schon beschrieben fängt meine Anzeige immer wieder bei Null an 
wenn der ADC_wert über 556 geht. WARUM?

das Program sieht folgendermaßen aus:

in Main:
unsigned int adcrohw
double VOUT, RH

                        lcd_putn(adcrohw);

                        VOUT = ((5000.0*(adcrohw))/1023.0);
      RH = (0.03892*VOUT-41.98);

      lcd_putfl(RH);

in lcd_putfl:

void lcd_putfl( double f )
{
    char Buffers[10];
    unsigned int i;

  i= (unsigned int)(f*1000);
  sprintf( Buffers, "%d.%03d", i / 1000, i % 1000 );
  lcd_puts( Buffers );

}

MCU mega32
Der ADC läuft mit externen Vref = VCC
ADMUX = 0x00 und prescaler 32

Ich habe schon alle anderen datentypen versucht und keinen Plan woran es 
liegen könnte.....

Autor: Karl Heinz (kbuchegg) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
In lcd_putfl:

    i= (unsigned int)(f*1000);

i ist ein unsigned int. 16 Bit. Maximalwert also 65535.
Wie gross darf daher dein f maximal sein, damit diese
Berechnung nicht überläuft?

   sprintf( Buffers, "%d.%03d", i / 1000, i % 1000 );

%d ist das Formatkennzeichen für einen signed int.
Daher kriegst du dann das negative Vorzeichen.

Autor: loki81 (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Leute ihr seid die größten!!!

@Karl Heinz
jepp genau so geht es. Danke

Meine C Zeiten sind schon was her hab mein altes Skript gestern raus 
geholt und das sagt uint =32Bit naja dem war dann wohl nicht so.

könnte ich denn uint_32 aus der inttypes benutzen? das müsste ja dann 
funsen denn mein f geht nur bis maximal 100.

naja vielen Dank noch mal

Autor: Εrnst B✶ (ernst)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
loki81 wrote:

>                         VOUT = ((5000.0*(adcrohw))/1023.0);

Das 1023.0 ist immernoch falsch, da gehört 1024.0 hin.
Ist zwar nur ein kleiner Fehler, aber ein komplett unnötiger.

Wenn du 5 € auf drei Leute verteilen sollst, gibst du doch auch nicht 
jedem 2,50 €.

Autor: loki81 (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@Ernst

Klar hast recht mit dem 1024. Hatte ich erst so und dann dachte ich 
vielleicht ist das ja der Grund für den überlauf und hab 1023 draus 
gemacht. Wenn man man mal richtig überlegen würde teile ich ja durch 
1024. Da kann gar kein Überlauf draus entstehen.
Ja aber wenn man schon 3 Std nach so nem dummen Fehler sucht wird man 
zum Hirsch... Hab das bestimmt 20 mal von 23 auf 24 und wieder zurück 
geproggt...

Aber ich finde den Einsatz echt klasse (zweiDaumenHoch)

loki

Autor: Johannes M. (johnny-m)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
loki81 wrote:
> Meine C Zeiten sind schon was her hab mein altes Skript gestern raus
> geholt und das sagt uint =32Bit naja dem war dann wohl nicht so.
Das ist plattformabhängig! Auf einer 32-Bit-CPU ist int meist 
tatsächlich 32 Bit breit, aber bei einer 8-Bit-Plattform sieht das 
anders aus.

Der C-Standard schreibt für int lediglich eine Mindestbreite von 16 
Bit vor. Im Normalfall entspricht int der "natürlichen" Breite des 
Systems, was bei einem 8-Bit-µC aber nicht geht, wegen der vorgegebenen 
Mindestbreite. Deshalb macht es gerade bei µCs oft Sinn, die Typen aus 
der stdint.h zu benutzen, weil man da immer sofort sieht, wie lang der 
Datentyp tatsächlich ist.

Und man muss eben bei Berechnungen dran denken, dass die in int 
durchgeführt werden, wenn nichts anderes angegeben ist bzw. wenn keiner 
der beteiligten Operanden größer als int ist (OK, in diesem Falle 
nützt einem die stdint.h nichts).

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.