0.2.3 Complex

This commit is contained in:
rob tillaart 2021-09-14 11:58:53 +02:00
parent 6bdb143712
commit 65a05739ca
7 changed files with 132 additions and 62 deletions

View File

@ -4,10 +4,14 @@ name: Arduino CI
on: [push, pull_request] on: [push, pull_request]
jobs: jobs:
arduino_ci: runTest:
runs-on: ubuntu-latest runs-on: ubuntu-latest
steps: steps:
- uses: actions/checkout@v2 - uses: actions/checkout@v2
- uses: Arduino-CI/action@master - uses: ruby/setup-ruby@v1
# Arduino-CI/action@v0.1.1 with:
ruby-version: 2.6
- run: |
gem install arduino_ci
arduino_ci.rb

View File

@ -1,26 +1,41 @@
[![Arduino CI](https://github.com/RobTillaart/Complex/workflows/Arduino%20CI/badge.svg)](https://github.com/marketplace/actions/arduino_ci) [![Arduino CI](https://github.com/RobTillaart/Complex/workflows/Arduino%20CI/badge.svg)](https://github.com/marketplace/actions/arduino_ci)
[![Arduino-lint](https://github.com/RobTillaart/Complex/actions/workflows/arduino-lint.yml/badge.svg)](https://github.com/RobTillaart/Complex/actions/workflows/arduino-lint.yml)
[![JSON check](https://github.com/RobTillaart/Complex/actions/workflows/jsoncheck.yml/badge.svg)](https://github.com/RobTillaart/Complex/actions/workflows/jsoncheck.yml)
[![License: MIT](https://img.shields.io/badge/license-MIT-green.svg)](https://github.com/RobTillaart/Complex/blob/master/LICENSE) [![License: MIT](https://img.shields.io/badge/license-MIT-green.svg)](https://github.com/RobTillaart/Complex/blob/master/LICENSE)
[![GitHub release](https://img.shields.io/github/release/RobTillaart/Complex.svg?maxAge=3600)](https://github.com/RobTillaart/Complex/releases) [![GitHub release](https://img.shields.io/github/release/RobTillaart/Complex.svg?maxAge=3600)](https://github.com/RobTillaart/Complex/releases)
# Complex # Complex
Arduino library for Complex math Arduino library for Complex mathematical operations.
## Description ## Description
This library defines the complex datatype and all the common math functions for it. This library defines the complex data type and all the common mathematical functions for it.
These functions include basic = "+ - \* /" and also power and goniometric functions.
The library implements the **Printable** interface so one can directly print the complex values
in any stream e.g. Serial.
These functions include basic = "+ - \* /" and also power and gonio functions.
## Interface ## Interface
See Complex.h for all functions implemented. See Complex.h for a full list of functions implemented.
The library uses **float** for the real and imaginary part so precision is limited.
Reasons are memory and performance, see also Future section below.
The library implements the constant **one** as this value is often used in the code.
## Note ## Note
The library has a big footprint so it fills up the memory of an UNO quite fast. The library has a big footprint so it fills up the memory of an UNO quite fast,
especially if all functionality is used.
#### Known problem #### Known problem
@ -30,9 +45,21 @@ Class does not compile for DUE and TEENSY
Apparently the name "Complex" is already in use (reserved) by some non-AVR compilers Apparently the name "Complex" is already in use (reserved) by some non-AVR compilers
so it won't include the Complex.h file. Problem seen on Due and Teensy3.5 so it won't include the Complex.h file. Problem seen on Due and Teensy3.5
#### Solution:
#### Solution
- Make a copy of the Complex Library and rename the folder to CComplex - Make a copy of the Complex Library and rename the folder to CComplex
- Rename Complex.h to CComplex.h - Rename Complex.h to CComplex.h
- Rename Complex.cpp to CComplec.cpp - Rename Complex.cpp to CComplex.cpp
- change one line in CComplex.cpp to include CComplex.h - change one line in CComplex.cpp to include CComplex.h
- note your sketches need to include CComplex.h too.
## Future
- create a (8 byte) double based variant for high precision e.g. Complex8()
Note that some platforms map double to float, others support float in hardware etc
so there is a big difference expected in both memory and performance
- create the constant **i** ??

View File

@ -1,30 +0,0 @@
ReleaseNote.txt - Complex Library
===================================================================================
2018/04/02
===========
Revert double to float.
===================================================================================
2018/01/29
===========
Fixed c_sin, c_cos, c_sinh, c_cosh
They contained an invalid optimization.
===================================================================================
2018/01/25
=============
Issue found in version 0.1.9 - https://github.com/RobTillaart/Arduino/issues/90
Class does not compile for DUE and TEENSY
Apparently the name "Complex" is already in use (reserved) by some non-AVR compilers
so it won't include the Complex.h file. Problem seen on Due and Teensy3.5
Solution:
- Make a copy of the Complex Library and rename the folder to CComplex
- Rename Complex.h to CComplex.h
- Rename Complex.cpp to CComplec.cpp
- change one line in CComplex.cpp to include CComplex.h
===================================================================================

View File

@ -1,24 +1,28 @@
// //
// FILE: Complex.cpp // FILE: Complex.cpp
// AUTHOR: Rob Tillaart // AUTHOR: Rob Tillaart
// VERSION: 0.2.2 // VERSION: 0.2.3
// PURPOSE: Arduino library for Complex math // PURPOSE: Arduino library for Complex math
// URL: https://github.com/RobTillaart/Complex // URL: https://github.com/RobTillaart/Complex
// http://arduino.cc/playground/Main/ComplexMath // http://arduino.cc/playground/Main/ComplexMath
// //
//
// 0.2.3 2021-09-14 fix build-CI + update readme
// 0.2.2 2020-12-16 add arduino-ci + unit test (starter) // 0.2.2 2020-12-16 add arduino-ci + unit test (starter)
// setReal, setImag // setReal, setImag
// 0.2.1 2020-06-05 fix library.json // 0.2.1 2020-06-05 fix library.json
// 0.2.0 2020-03-29 #pragma once, own repo // 0.2.0 2020-03-29 #pragma once, own repo
// 0.1.12 - 2018-04-02 - fix issue #33 double -> float // 0.1.12 2018-04-02 - fix issue #33 double -> float
// 0.1.11 - 2018-01-29 - fix sin and cos formula - issue #91 // 0.1.11 2018-01-29 - fix sin and cos formula - issue #91
// 0.1.10 - 2018-01-15 - uppercase #define COMPLEX_H // 0.1.10 2018-01-15 - uppercase #define COMPLEX_H
// 0.1.09 - 2016-10-15 - added (0,0) constructor // 0.1.09 2016-10-15 - added (0,0) constructor
// 0.1.08 - 2015-06-03 - refactor // 0.1.08 2015-06-03 - refactor
// 0.1.07 - 2015-06-03 - refactor interfaces // 0.1.07 2015-06-03 - refactor interfaces
#include "Complex.h" #include "Complex.h"
// PRINTING // PRINTING
size_t Complex::printTo(Print& p) const size_t Complex::printTo(Print& p) const
{ {
@ -30,12 +34,14 @@ size_t Complex::printTo(Print& p) const
return n; return n;
}; };
void Complex::polar(const float modulus, const float phase) void Complex::polar(const float modulus, const float phase)
{ {
re = modulus * cos(phase); re = modulus * cos(phase);
im = modulus * sin(phase); im = modulus * sin(phase);
} }
Complex Complex::reciprocal() Complex Complex::reciprocal()
{ {
float f = 1.0 / (re * re + im * im); float f = 1.0 / (re * re + im * im);
@ -44,35 +50,45 @@ Complex Complex::reciprocal()
return Complex(r, i); return Complex(r, i);
} }
//
// EQUALITIES // EQUALITIES
//
bool Complex::operator == (const Complex &c) bool Complex::operator == (const Complex &c)
{ {
return (re == c.re) && (im == c.im); return (re == c.re) && (im == c.im);
} }
bool Complex::operator != (const Complex &c) bool Complex::operator != (const Complex &c)
{ {
return (re != c.re) || (im != c.im); return (re != c.re) || (im != c.im);
} }
//
// NEGATE // NEGATE
//
Complex Complex::operator - () Complex Complex::operator - ()
{ {
return Complex(-re, -im); return Complex(-re, -im);
} }
//
// BASIC MATH // BASIC MATH
//
Complex Complex::operator + (const Complex &c) Complex Complex::operator + (const Complex &c)
{ {
return Complex(re + c.re, im + c.im); return Complex(re + c.re, im + c.im);
} }
Complex Complex::operator - (const Complex &c) Complex Complex::operator - (const Complex &c)
{ {
return Complex(re - c.re, im - c.im); return Complex(re - c.re, im - c.im);
} }
Complex Complex::operator * (const Complex &c) Complex Complex::operator * (const Complex &c)
{ {
float r = re * c.re - im * c.im; float r = re * c.re - im * c.im;
@ -80,6 +96,7 @@ Complex Complex::operator * (const Complex &c)
return Complex(r, i); return Complex(r, i);
} }
Complex Complex::operator / (const Complex &c) Complex Complex::operator / (const Complex &c)
{ {
float f = 1.0/(c.re * c.re + c.im * c.im); float f = 1.0/(c.re * c.re + c.im * c.im);
@ -88,6 +105,7 @@ Complex Complex::operator / (const Complex &c)
return Complex(r, i); return Complex(r, i);
} }
Complex& Complex::operator += (const Complex &c) Complex& Complex::operator += (const Complex &c)
{ {
re += c.re; re += c.re;
@ -95,6 +113,7 @@ Complex& Complex::operator += (const Complex &c)
return *this; return *this;
} }
Complex& Complex::operator -= (const Complex &c) Complex& Complex::operator -= (const Complex &c)
{ {
re -= c.re; re -= c.re;
@ -102,6 +121,7 @@ Complex& Complex::operator -= (const Complex &c)
return *this; return *this;
} }
Complex& Complex::operator *= (const Complex &c) Complex& Complex::operator *= (const Complex &c)
{ {
float r = re * c.re - im * c.im; float r = re * c.re - im * c.im;
@ -111,6 +131,7 @@ Complex& Complex::operator *= (const Complex &c)
return *this; return *this;
} }
Complex& Complex::operator /= (const Complex &c) Complex& Complex::operator /= (const Complex &c)
{ {
float f = 1.0/(c.re * c.re + c.im * c.im); float f = 1.0/(c.re * c.re + c.im * c.im);
@ -121,6 +142,7 @@ Complex& Complex::operator /= (const Complex &c)
return *this; return *this;
} }
// //
// POWER FUNCTIONS // POWER FUNCTIONS
// //
@ -131,6 +153,7 @@ Complex Complex::c_sqr()
return Complex(r, i); return Complex(r, i);
} }
Complex Complex::c_sqrt() Complex Complex::c_sqrt()
{ {
float m = modulus(); float m = modulus();
@ -140,12 +163,14 @@ Complex Complex::c_sqrt()
return Complex(r, i); return Complex(r, i);
} }
Complex Complex::c_exp() Complex Complex::c_exp()
{ {
float e = exp(re); float e = exp(re);
return Complex(e * cos(im), e * sin(im)); return Complex(e * cos(im), e * sin(im));
} }
Complex Complex::c_log() Complex Complex::c_log()
{ {
float m = modulus(); float m = modulus();
@ -154,6 +179,7 @@ Complex Complex::c_log()
return Complex(log(m), p); return Complex(log(m), p);
} }
Complex Complex::c_pow(const Complex &c) Complex Complex::c_pow(const Complex &c)
{ {
Complex t = c_log(); Complex t = c_log();
@ -161,17 +187,20 @@ Complex Complex::c_pow(const Complex &c)
return t.c_exp(); return t.c_exp();
} }
Complex Complex::c_logn(const Complex &c) Complex Complex::c_logn(const Complex &c)
{ {
Complex t = c; Complex t = c;
return c_log()/t.c_log(); return c_log()/t.c_log();
} }
Complex Complex::c_log10() Complex Complex::c_log10()
{ {
return c_logn(10); return c_logn(10);
} }
// //
// GONIO I - SIN COS TAN // GONIO I - SIN COS TAN
// //
@ -180,11 +209,13 @@ Complex Complex::c_sin()
return Complex(sin(re) * cosh(im), cos(re) * sinh(im)); return Complex(sin(re) * cosh(im), cos(re) * sinh(im));
} }
Complex Complex::c_cos() Complex Complex::c_cos()
{ {
return Complex(cos(re) * cosh(im), -sin(re) * sinh(im)); return Complex(cos(re) * cosh(im), -sin(re) * sinh(im));
} }
Complex Complex::c_tan() Complex Complex::c_tan()
{ {
/* faster but 350 bytes longer!! /* faster but 350 bytes longer!!
@ -205,6 +236,7 @@ Complex Complex::c_tan()
return c_sin() / c_cos(); return c_sin() / c_cos();
} }
Complex Complex::gonioHelper1(const byte mode) Complex Complex::gonioHelper1(const byte mode)
{ {
Complex c = (one - this->c_sqr()).c_sqrt(); Complex c = (one - this->c_sqr()).c_sqrt();
@ -220,21 +252,25 @@ Complex Complex::gonioHelper1(const byte mode)
return c; return c;
} }
Complex Complex::c_asin() Complex Complex::c_asin()
{ {
return gonioHelper1(0); return gonioHelper1(0);
} }
Complex Complex::c_acos() Complex Complex::c_acos()
{ {
return gonioHelper1(1); return gonioHelper1(1);
} }
Complex Complex::c_atan() Complex Complex::c_atan()
{ {
return (Complex(0,-1) * (Complex(re, im - 1)/Complex(-re, -im - 1)).c_log()) * 0.5; return (Complex(0,-1) * (Complex(re, im - 1)/Complex(-re, -im - 1)).c_log()) * 0.5;
} }
// //
// GONIO II - CSC SEC COT // GONIO II - CSC SEC COT
// //
@ -243,31 +279,37 @@ Complex Complex::c_csc()
return one / c_sin(); return one / c_sin();
} }
Complex Complex::c_sec() Complex Complex::c_sec()
{ {
return one / c_cos(); return one / c_cos();
} }
Complex Complex::c_cot() Complex Complex::c_cot()
{ {
return one / c_tan(); return one / c_tan();
} }
Complex Complex::c_acsc() Complex Complex::c_acsc()
{ {
return (one / *this).c_asin(); return (one / *this).c_asin();
} }
Complex Complex::c_asec() Complex Complex::c_asec()
{ {
return (one / *this).c_acos(); return (one / *this).c_acos();
} }
Complex Complex::c_acot() Complex Complex::c_acot()
{ {
return (one / *this).c_atan(); return (one / *this).c_atan();
} }
// //
// GONIO HYPERBOLICUS I // GONIO HYPERBOLICUS I
// //
@ -276,16 +318,19 @@ Complex Complex::c_sinh()
return Complex(cos(im) * sinh(re), sin(im) * cosh(re)); return Complex(cos(im) * sinh(re), sin(im) * cosh(re));
} }
Complex Complex::c_cosh() Complex Complex::c_cosh()
{ {
return Complex(cos(im) * cosh(re), sin(im) * sinh(re)); return Complex(cos(im) * cosh(re), sin(im) * sinh(re));
} }
Complex Complex::c_tanh() Complex Complex::c_tanh()
{ {
return c_sinh() / c_cosh(); return c_sinh() / c_cosh();
} }
Complex Complex::gonioHelper2(const byte mode) Complex Complex::gonioHelper2(const byte mode)
{ {
Complex c = c_sqr(); Complex c = c_sqr();
@ -301,16 +346,19 @@ Complex Complex::gonioHelper2(const byte mode)
return c; return c;
} }
Complex Complex::c_asinh() Complex Complex::c_asinh()
{ {
return gonioHelper2(0); return gonioHelper2(0);
} }
Complex Complex::c_acosh() Complex Complex::c_acosh()
{ {
return gonioHelper2(1); return gonioHelper2(1);
} }
Complex Complex::c_atanh() Complex Complex::c_atanh()
{ {
Complex c = (*this + one).c_log(); Complex c = (*this + one).c_log();
@ -318,6 +366,7 @@ Complex Complex::c_atanh()
return c * 0.5; return c * 0.5;
} }
// //
// GONIO HYPERBOLICUS II // GONIO HYPERBOLICUS II
// //
@ -326,26 +375,31 @@ Complex Complex::c_csch()
return one / c_sinh(); return one / c_sinh();
} }
Complex Complex::c_sech() Complex Complex::c_sech()
{ {
return one / c_cosh(); return one / c_cosh();
} }
Complex Complex::c_coth() Complex Complex::c_coth()
{ {
return one / c_tanh(); return one / c_tanh();
} }
Complex Complex::c_acsch() Complex Complex::c_acsch()
{ {
return (one / *this).c_asinh(); return (one / *this).c_asinh();
} }
Complex Complex::c_asech() Complex Complex::c_asech()
{ {
return (one / *this).c_acosh(); return (one / *this).c_acosh();
} }
Complex Complex::c_acoth() Complex Complex::c_acoth()
{ {
return (one / *this).c_atanh(); return (one / *this).c_atanh();

View File

@ -2,16 +2,19 @@
// //
// FILE: Complex.h // FILE: Complex.h
// AUTHOR: Rob Tillaart // AUTHOR: Rob Tillaart
// VERSION: 0.2.2 // VERSION: 0.2.3
// PURPOSE: Arduino library for Complex math // PURPOSE: Arduino library for Complex math
// URL: https://github.com/RobTillaart/Complex // URL: https://github.com/RobTillaart/Complex
// http://arduino.cc/playground/Main/ComplexMath // http://arduino.cc/playground/Main/ComplexMath
// //
#include "Arduino.h" #include "Arduino.h"
#include "Printable.h" #include "Printable.h"
#define COMPLEX_LIB_VERSION "0.2.2"
#define COMPLEX_LIB_VERSION "0.2.3"
class Complex: public Printable class Complex: public Printable
{ {
@ -19,14 +22,17 @@ public:
Complex(const float r = 0, const float i = 0) : re(r), im(i) {}; Complex(const float r = 0, const float i = 0) : re(r), im(i) {};
Complex(const Complex &c) : re(c.re), im(c.im) {}; Complex(const Complex &c) : re(c.re), im(c.im) {};
void set(const float r, const float i ) { re = r; im = i; }; void set(const float r, const float i ) { re = r; im = i; };
void setReal(const float r) { re = r; }; void setReal(const float r) { re = r; };
void setImag(const float i ) { im = i; }; void setImag(const float i ) { im = i; };
float real() { return re; }; float real() { return re; };
float imag() { return im; }; float imag() { return im; };
size_t printTo(Print& p) const; size_t printTo(Print& p) const;
void polar(const float modulus, const float phase); void polar(const float modulus, const float phase);
float phase() { return atan2(im, re); }; float phase() { return atan2(im, re); };
float modulus() { return hypot(re, im); }; float modulus() { return hypot(re, im); };
@ -34,11 +40,14 @@ public:
Complex conjugate() { return Complex(re, -im); }; Complex conjugate() { return Complex(re, -im); };
Complex reciprocal(); Complex reciprocal();
bool operator == (const Complex&); bool operator == (const Complex&);
bool operator != (const Complex&); bool operator != (const Complex&);
Complex operator - (); // negation Complex operator - (); // negation
Complex operator + (const Complex&); Complex operator + (const Complex&);
Complex operator - (const Complex&); Complex operator - (const Complex&);
Complex operator * (const Complex&); Complex operator * (const Complex&);
@ -49,6 +58,7 @@ public:
Complex& operator *= (const Complex&); Complex& operator *= (const Complex&);
Complex& operator /= (const Complex&); Complex& operator /= (const Complex&);
Complex c_sqrt(); Complex c_sqrt();
Complex c_sqr(); Complex c_sqr();
Complex c_exp(); Complex c_exp();
@ -57,6 +67,7 @@ public:
Complex c_pow(const Complex &); Complex c_pow(const Complex &);
Complex c_logn(const Complex &); Complex c_logn(const Complex &);
Complex c_sin(); Complex c_sin();
Complex c_cos(); Complex c_cos();
Complex c_tan(); Complex c_tan();
@ -64,6 +75,7 @@ public:
Complex c_acos(); Complex c_acos();
Complex c_atan(); Complex c_atan();
Complex c_csc(); Complex c_csc();
Complex c_sec(); Complex c_sec();
Complex c_cot(); Complex c_cot();
@ -71,6 +83,7 @@ public:
Complex c_asec(); Complex c_asec();
Complex c_acot(); Complex c_acot();
Complex c_sinh(); Complex c_sinh();
Complex c_cosh(); Complex c_cosh();
Complex c_tanh(); Complex c_tanh();
@ -78,6 +91,7 @@ public:
Complex c_acosh(); Complex c_acosh();
Complex c_atanh(); Complex c_atanh();
Complex c_csch(); Complex c_csch();
Complex c_sech(); Complex c_sech();
Complex c_coth(); Complex c_coth();
@ -85,6 +99,7 @@ public:
Complex c_asech(); Complex c_asech();
Complex c_acoth(); Complex c_acoth();
protected: protected:
float re; float re;
float im; float im;

View File

@ -1,7 +1,7 @@
{ {
"name": "Complex", "name": "Complex",
"keywords": "Complex,numbers,Imaginary,phase,modulus,polar,conjugate,math,sin,cos,tan,exp,pow", "keywords": "Complex,numbers,Imaginary,phase,modulus,polar,conjugate,math,sin,cos,tan,exp,pow",
"description": "Library for Complex math.", "description": "Library for Complex math. Implements Printable interface.",
"authors": "authors":
[ [
{ {
@ -15,7 +15,7 @@
"type": "git", "type": "git",
"url": "https://github.com/RobTillaart/Complex.git" "url": "https://github.com/RobTillaart/Complex.git"
}, },
"version": "0.2.2", "version": "0.2.3",
"license": "MIT", "license": "MIT",
"frameworks": "arduino", "frameworks": "arduino",
"platforms": "*" "platforms": "*"

View File

@ -1,9 +1,9 @@
name=Complex name=Complex
version=0.2.2 version=0.2.3
author=Rob Tillaart <rob.tillaart@gmail.com> author=Rob Tillaart <rob.tillaart@gmail.com>
maintainer=Rob Tillaart <rob.tillaart@gmail.com> maintainer=Rob Tillaart <rob.tillaart@gmail.com>
sentence=Arduino library for Complex math. sentence=Arduino library for Complex math.
paragraph= paragraph=implements Printable interface
category=Data Processing category=Data Processing
url=https://github.com/RobTillaart/Complex url=https://github.com/RobTillaart/Complex
architectures=* architectures=*