Oft verwenden wir Mikrocontroller, um Dinge in unseren Robotern zu erledigen, müssen aber einige Berechnungen in Dezimalzahlen durchführen. Die Verwendung von Gleitkommavariablen ist sehr langsam, da automatisch eine Software-Gleitkomma-Bibliothek enthalten ist (es sei denn, Sie haben einen High-End-Mikrocontroller). Daher verwenden wir im Allgemeinen eine Festkomma-Arithmetik.
Immer wenn ich das mache, verwende ich einfach eine ganze Zahl und erinnere mich, wo die Dezimalstelle ist. Es muss jedoch sorgfältig darauf geachtet werden, dass alles konsistent ist, insbesondere wenn Berechnungen Variablen beinhalten, bei denen sich der Dezimalpunkt an einer anderen Stelle befindet.
Ich habe eine Festpunkt-atan2-Funktion implementiert, aber da ich versucht habe, jeden letzten Tropfen mit begrenzter Genauigkeit (16 Bit) zu komprimieren, habe ich häufig die Definition des Dezimalpunkts geändert und sie hat sich geändert, als ich sie optimiert habe. Außerdem hätte ich einige Konstanten als Quasi-Nachschlagetabelle, die selbst irgendwo einen impliziten Dezimalpunkt haben.
Ich möchte wissen, ob es einen besseren Weg gibt. Gibt es eine Bibliothek oder einen Satz von Makros, die die Verwendung von Festkommavariablen vereinfachen, die Multiplikation und Division zwischen gemischten Variablen vereinfachen und die Deklaration von Dezimalzahlen oder konstanten Ausdrücken ermöglichen, aber beim Kompilieren automatisch in die gewünschte Festkommadarstellung konvertieren können? Zeit?
quelle
Antworten:
Es wäre schön, wenn wir dem Compiler den Bereich und die Genauigkeit jeder Festkomma-Eingangsvariablen mitteilen könnten (vielleicht keine zwei mit dem Radix-Punkt an derselben Stelle), und es würde automatisch - zur Kompilierungszeit - den richtigen Bereich verwenden und Präzisions- und Neuskalierungsoperationen für die Zwischen- und Endwerte in einer Reihe von Berechnungen. Ich habe Gerüchte gehört, dass dies in der Programmiersprache Ada oder in C ++ - Vorlagen möglich sein könnte.
Leider sind Festpunkt-Arithmetikbibliotheken am nächsten, bei denen Sie als Programmierer die richtige Darstellung manuell auswählen und manuell überprüfen müssen, ob jede Operation einen angemessenen Bereich und eine angemessene Genauigkeit aufweist. Manchmal erleichtern sie die Multiplikation und Division zwischen gemischten Variablen. Sowie:
quelle
Ich habe die TI IQMath-Bibliothek verwendet , um virtuelles Gleitkomma auf ihren Festkomma-DSPs zu implementieren.
Das verwendet einige TI-spezifische Dinge, aber ich habe diesen Code auch als Basis verwendet, um virtuelle Gleitkomma-Mathematik auf anderen Mikrocontrollern zu implementieren. Das Portieren erfordert ein wenig Arbeit, ist aber viel einfacher als bei Null anzufangen.
quelle
Es gibt eine Reihe von Implementierungen (keine Bibliotheken, die mir sofort bekannt sind) der binären Skalierung (auch bekannt als B-Skalierung).
In diesem Fall behalten Sie eine mentale Notiz (oder dokumentieren noch besser den Code ...) darüber, wo sich der Dezimalpunkt befindet, und verschieben den Dezimalpunkt mithilfe von Verschiebungen nach oben oder unten.
Ich habe B-Skalierung in Assembler bei Verteidigungsprojekten verwendet, selbst bei kleinsten CPUs, damit ich für die Eignung für alles andere bürgen kann ...
quelle
Wenn Sie eine Ganzzahl verwenden, um sich zu merken, wo sich der "Punkt" befindet, verwenden sie eine Art Gleitkomma-Arithmetik. Fixpunkt, hat wirklich Fixpunkt .
atan
cos
Dies hängt vom Wertebereich ab, den Ihre Anwendung benötigt. Möglicherweise möchten Sie jedoch vollständig zu einer Festpunktdarstellung wechseln. Das heißt zum Beispiel, anstatt eine Nummer wie diese zu behalten:
Wo
number
ist die ganze Zahl unddecimal_point
sagt, wo der Dezimalpunkt ist, können Sie es wie folgt speichern:wobei die ganze Zahl ist
integer.fraction
, die die gleiche Speichernutzung hat, einen höheren Wertebereich hat und im Allgemeinen einfacher zu verwenden ist.quelle
#define
, oder? Ich dachte, Sie speichern es tatsächlich und es kann variieren, je nachdem, wie groß oder klein Ihre Nummer ist.