mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik Rechnen mit Strings, wie geht das?Bascom


Autor: Neubert Uwe (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hi! Ich habe ein Problem, ich muss kleine Berechnungen in meinem
Programm ausführen.

Dim Zahl1 as String*2
Dim Zahl2 as String*2
Dim Ergebnis as String*4

Ich nutze diese Sache in einem Programm, welches einen Timer laufen
lässt.Der Wert der Sekunden soll erst nach einem geschlossenen Schalter
abgespeichert werden und steht mir dann als fester Wert zur Verfügung.
Dieser liegt dann als String mit Namen Zahl1 vor.

Zahl2 ist stets fortlaufend im Programm, also die ständig ablaufende
Zeit, kann also mal 00 und mal 59 sein. :-)

Nun mein Problem : Ich will Zahl1 von der Zahl2 abziehen!

Ergebnis = Zahl2 - Zahl2
Dies geht offensichtlich nicht (habe im Forum gelesen, man kann mit
Strings nicht rechnen :-(  ) Was kann ich tun? Die Strings würde ich
gern so belassen wenn es geht. Möchte sie nur umwandeln, vieleicht in
word?

MFG Uwe!

Autor: Stefan (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Bascom hat doch sicher Funktionen mit denen man einen String in eine
Zahl umwandeln kann und umgekehrt...

Lies mal im Handbuch zu VAL und STR nach. Online z.B. bei
http://de.wikibooks.org/wiki/Quick_Basic:_Val,_Str

Damit wäre die Berechnung:
Ergebnis = STR(VAL(Zahl2) - VAL(Zahl2))

Autor: Peter Dannegger (peda)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Gerechnet wird immer nur im Binärsystem, weil das für die CPU am
schnellsten geht.
Außerdem wäre es Speicherplatzverschwendung, wenn man für die
verschiedensten Zahlensysteme extra Mathe-Bibliotheken schreiben
würde.


Wenn Zahlen als Text vorliegen, mußt Du sie umwandeln, je nachdem, ob
sie dual, oktal, dezimal, hexadezimal oder float sind.


Peter

Autor: Uwe Neubert (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Danke, das reicht mir schon. Ich habe das geschafft was ich wollte. Zum
Glück habe ich genug Speicher frei und muss mir darum keine Sorgen
machen. Die mache ich mir mal später wenn ich mehr Firm bin auf dem
Gebiet. Momentan reicht das noch für meine Versuche.

Nun mach ich mich an den kleinen Fehler der noch in meiner Formel
steckt. Folgendes: Die Zeit zählt intern hoch von 00 bis 59. Nun wollte
ich ganz schlau sein und diese Zeit nutzen um ab einem Ereignis, ein
Schalter wird geschlossen, eine zweite Zeit im Display anzuzeigen. Eben
ab dem Zeitpunkt von 00 beginnend und dann weiterzähelnd. Daher habe ich
einfach die "Stammzeit" , angenommen 40 sekunden festgeschrieben. Nun
zieht mein Programm immer 40 Sekunden von der im Hintergrund laufenden
ab. Ergebnis ist anfänglich noch 00. Aber wenn diese dann später 00
erreicht, so ergibt sich ein negatives Erge´bnis! > 00-40 =-40 :-( Mal
sehen was ich da nun mache...

Autor: Profi (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
In diesem Fall kannst Du die Sekunden seit 0:00 zählen / berechnen und
dann subtrahieren.
Dummerweise hat ein Tag 86400 Sekunden, passt nicht mehr in 16 Bits.
Also long verwenden oder jede 2. Sekunde zählen.
Formel:
s = 3600*hh + 60*mm + ss

Autor: Neubert Uwe (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@ Profi:

Danke, dass du dir da Gedanken gamacht hast! Nur verstehe ich nicht
ganz was du meinst. Das Programm zählt die Zeit seit einschalten oder
Reset und zeigt sie auch in der Form MM:SS an. Nun will ich aber diese
Zeit umrechnen. Also wenn mein Schalter am Eingang an ist, dann soll
eine zweite Zeit loslaufen. Ich muss also ab diesem Zeitpunkt diese
MM:SS so umrechnen, dass sie die Zeit seit diesem Punkt anzeigt. Das
schaffe ich einfach nicht... Wie ist deine Formel gemeint? Ich hatte
ursprünglich versucht einfach die laufende Zeit als Variable
festzuschreiben und zu speichern. Danach wollte ich einfach diesen Wert
von der fortlaufenden Zeit abziehen und komme so in negative Zahlen. ;-(
Wahrscheinlich hast du die richtige Lösung aber ich sehe nicht durch ;-)

Autor: Profi (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Entweder Du zählst nur Sekunden (seit dem Einschalten in einer Variablen
und seit dem Kontaktschließen in einer anderen) und rechnest die
Sekunden in der Anzeigeroutine ins Format MM:SS um.
MM=sek div 60; (Integer-Division)
SS=sek mod 60; (Integer-Modulo)

Oder Du zählst die Zeit im Format MM:SS und rechnest zurück, ist aber
umständlicher.

Erklär mal genauer, in welchem Bereich die Zeiten liegen können.

Autor: Karl heinz Buchegger (kbucheg)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
> Danach wollte ich einfach diesen Wert von der fortlaufenden Zeit
> abziehen und komme so in negative Zahlen

Wo liegt das Problem mit negativen Zahlen?

Wenn deine erste Zeit 02:55
und die zweite Zeit 04:15
ist, was ist dann die Differenz (vorher nachdenken, ev. Finger
zu hilfe nehmen. Erst dann ausrechnen).

04 - 02  ->     2  Minuten
15 - 55  ->  - 40  Sekunden

Da es aber keine -40 Sekunden gibt, rechnen wir 1 Minute weniger
und dafür 60 Sekunden dazu:

  aus 2 Minuten wird also 1 Minuntend dafür kommt bei den
Sekunden 60 dazu:  -40 + 60 -> 20

Die Zeitdifferenz ist also 1 Minute 20 Sekunden.

Autor: Karl heinz Buchegger (kbucheg)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Selbiges in die andere Richtung.

Wenn du eine Zeit hast

   5 : 32

welches ist dann der Zeitpunkt 47 Sekunden früher?

32 - 47  -> -15 Sekunden

Da wir aber keine -15 Sekunden auf der Uhr haben, ziehen wir von
den Minuten 1 ab, und dafür bei den Sekunden wieder 60 dazu:

   -15 + 60  -> 45
     5 -  1  ->  4

d.h. der Zeitpunkt 4:45 liegt genau 47 Sekunden vor dem
Zeitpunkt 5:32

Autor: Karl heinz Buchegger (kbucheg)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ach ja noch was:

> Dieser liegt dann als String mit Namen Zahl1 vor.

Da du hier rechnen musst, ist das keine so gute Idee.
Ein String ist einfach nur ein Text. Nicht mehr und nicht weniger.
Es ist daher nicht so schlau so früh wie möglich auf Strings
zu wechseln( Ich nehme mal an du machst das wegen der Ausgabe),
sondern so spät wie möglich. Halte dir Zahlen als Zahlen und
bilde erst dann Strings aus den Zahlen wenn du alles fertig
berechnet hast.

Autor: Neubert Uwe (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ich denke ich habs begriffen. Danke dafür! Habe das zwischenzeitlich so
gelöst:

Meine feste Zeit ist angenommen 20 Sekunden. Die andere läuft weiter.
Also ist mein Ergebnis Zeit2 - Zeit1 , also 20 - 20 = 0 Sekunden. Bei
Zahl 2 = 21 wäre dann eine Sekunde vergangen. 21-20 = 1.
Das kann man solange treiben solange Zeit2 größer Zeit1 ist!!! Danach
muss man das umdrehen.
Also:

If Zeit2 > Zeit1 then
Ergebnis = Zeit2 - Zeit1
end if

If Zeit2 = Zeit1 then
Ergebnis = Zeit2 - Zeit1
end if

So, wenn das nun anders ist läufts folgendermaßen:

If Zeit1 > Zeit2 then
Ergebnis = Zeit2 - Zeit1
Ergebnis = Ergebnis + 60
end if

Vielleicht ist das idiotisch aber es funzt. :-)

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

Bewertung
0 lesenswert
nicht lesenswert
Du hast eines immer noch nicht geschnallt:
Wenn du mit Minuten:Sekunden rechnest, dann kannst du
nicht einfach nur die Sekunden korrigiern und alles
ist gut.

Das ist so wie bei Meter und Kilometer:
Wenn du ( 1 km und 670 Meter) zu ( 3 km und 497 Meter )addieren
musst, dann rechnest du
   1 km + 3 km    ergibt 4 km
 670 m  + 497 m   ergibt 1167 m

Nun steckt aber in den 1167 Metern selbst wieder ein Kilometer.
Diesen 1 km (also die 1000 Meter) ziehst du von den 1167 ab
(macht daher 167 Meter) und dafür kommt bei den ganzen km einer
dazu.

Das Ergebnis ist also  5 km und 167 Meter.

Bei einer Uhr ist das bei Minuten und Sekunden (und Stunden) genau
das gleiche. Nur das hier halt 60 Sekunden eine Minute bilden
und nicht 1000. Aber das Prinzip ist völlig identisch.

Alternativ (und das ist oft nicht die schlechteste Lösung), rechnest
du in der kleinsten Einheit. Anstatt dem ganzen Gepfriemel von da oben
rechnest du in der Einheit Meter.
Dann hast du von vorne herein gar keine ( 1km und 670 Meter) sondern
nur 1670 Meter. Genauso hast du im zweiten Fall keine 3km und
 497 Meter, sondern 3497 Meter.
Jetzt ist die Addition einfach: 1670 + 3497 ergibt 5167
Wenn alles fertig gerechnet ist, wird das dann zu Anzeigezwecken
wieder in km und Meter umgewandelt: 5 km 167 Meter.

Analog kann man das ganze bei Zeiten machen, wenn man nur
berücksichtigt, dass 1 Minute aus 60 Sekunden besteht.

Anstatt mich also damit abzuquälen wie ich 23 Minuten und 12 Sekunden
von 48 Minuten und 53 Sekunden abziehe, verwandle ich alles
in Sekunden.

23m 12s   ->  23 * 60 + 12 -> 1392 Sekunden
48m 53s   ->  48 * 60 + 53 -> 2933 Sekunden

Und jezt kann ich wieder ganz leicht subtrahieren:
2933 - 1392 -> 1541 Sekunden

Will ich wissen, wie lange 1541 Sekunden sind, dann rechne ich:

1541 / 60 = 25
1541 - ( 60 * 25 ) = 41

1541 Sekunden sind also 25 Minuten und 41 Sekunden.

Der springende Punkt ist der, dass ich eine Angabe von Minuten
und Sekunden sofort (bei einer Eingabe oder wo auch immer ich
die Werte herkriege) in reinrassige Sekunden umwandle. Dann kann
ich rechnen wie ich lustig bin, ich arbeite immer nur mit Sekunden.
Erst dann, wenn ich das Ergebnis anzeige, erst dann werden die
reinen Sekunden wieder in eine Form Minuten:Sekunden umgewandelt.

Autor: Uwe Neubert (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Das ist eine Spitzen Idee! So werde ich das nun machen. Nach meinem
Vorhaben bin ich übrigens auch mit dem Minuten so verfahren. Und das
ging nicht. Nach deinem Prinzip ists einleuchtend. Vielen Dank dafür!

Autor: Johngun (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Schön,
Vor 25 Jahren war ich der Basic Freak.
Jetzt weiß ich endlich warum ich das Ding nicht zum Rechnen kriege.

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.