ccode atan2 generates nan
6 visualizaciones (últimos 30 días)
Mostrar comentarios más antiguos
Hi!
I have the following question related to the ccode function of the symbolic toolbox.
Let us consider the following piece of code:
syms a b real
ccode(atan2(a,b))
the result is:
' t0 = log((a*sqrt(-1.0)+b)/fabs(a*sqrt(-1.0)+b))*-sqrt(-1.0);'
Questions for the MathWorks:
1. Why ccode replace the atan2 function (which is available in c) with such log implementation?
2. There is a way to prevent such replacement (some additional optional parameter?)
The following Matlab script has been written to generate I/O pairs for the atan2 function to compare the output of the Matlab atan2 vs the C vs the ccode output:
p = -2:1:2;
[X,Y] = meshgrid(p,p);
Z = zeros(size(X));
for i=1:size(X,1)
for j=1:size(X,2)
Z(i,j) = atan2(Y(i,j),X(i,j));
end
end
And with those data I ran the following C code (Visual Studio)
#include "stdafx.h"
#include "math.h"
#include "complex.h"
double Atan2(double a, double b) {
return log((a*sqrt(-1.0) + b) / fabs(a*sqrt(-1.0) + b))*-sqrt(-1.0);
}
int main()
{
const unsigned int nTest = 25;
const double adX[nTest] = { -2.000000, -2.000000, -2.000000, -2.000000, -2.000000, -1.000000, -1.000000, -1.000000, -1.000000, -1.000000, 0.000000, 0.000000, 0.000000, 0.000000, 0.000000, 1.000000, 1.000000, 1.000000, 1.000000, 1.000000, 2.000000, 2.000000, 2.000000, 2.000000, 2.000000, };
const double adY[nTest] = { -2.000000, -1.000000, 0.000000, 1.000000, 2.000000, -2.000000, -1.000000, 0.000000, 1.000000, 2.000000, -2.000000, -1.000000, 0.000000, 1.000000, 2.000000, -2.000000, -1.000000, 0.000000, 1.000000, 2.000000, -2.000000, -1.000000, 0.000000, 1.000000, 2.000000, };
const double adZ[nTest] = { -2.356194, -2.677945, 3.141593, 2.677945, 2.356194, -2.034444, -2.356194, 3.141593, 2.356194, 2.034444, -1.570796, -1.570796, 0.000000, 1.570796, 1.570796, -1.107149, -0.785398, 0.000000, 0.785398, 1.107149, -0.785398, -0.463648, 0.000000, 0.463648, 0.785398, };
unsigned int nIdx = 0;
for (nIdx = 0; nIdx < nTest; nIdx++) {
printf("atan2(%+05.5f,%+05.5f)= Matlab(%+05.5f) C(%+05.5f) CCODE(%+05.5f)\n",
adY[nIdx], adX[nIdx],
adZ[nIdx],
atan2(adY[nIdx], adX[nIdx]),
Atan2(adY[nIdx], adX[nIdx]));
}
scanf("%d", &nIdx);
return 0;
}
The results are presented here:
atan2(-2.00000,-2.00000)= Matlab(-2.35619) C(-2.35619) CCODE(-nan(ind))
atan2(-1.00000,-2.00000)= Matlab(-2.67794) C(-2.67795) CCODE(-nan(ind))
atan2(+0.00000,-2.00000)= Matlab(+3.14159) C(+3.14159) CCODE(-nan(ind))
atan2(+1.00000,-2.00000)= Matlab(+2.67794) C(+2.67795) CCODE(-nan(ind))
atan2(+2.00000,-2.00000)= Matlab(+2.35619) C(+2.35619) CCODE(-nan(ind))
atan2(-2.00000,-1.00000)= Matlab(-2.03444) C(-2.03444) CCODE(-nan(ind))
atan2(-1.00000,-1.00000)= Matlab(-2.35619) C(-2.35619) CCODE(-nan(ind))
atan2(+0.00000,-1.00000)= Matlab(+3.14159) C(+3.14159) CCODE(-nan(ind))
atan2(+1.00000,-1.00000)= Matlab(+2.35619) C(+2.35619) CCODE(-nan(ind))
atan2(+2.00000,-1.00000)= Matlab(+2.03444) C(+2.03444) CCODE(-nan(ind))
atan2(-2.00000,+0.00000)= Matlab(-1.57080) C(-1.57080) CCODE(-nan(ind))
atan2(-1.00000,+0.00000)= Matlab(-1.57080) C(-1.57080) CCODE(-nan(ind))
atan2(+0.00000,+0.00000)= Matlab(+0.00000) C(+0.00000) CCODE(-nan(ind))
atan2(+1.00000,+0.00000)= Matlab(+1.57080) C(+1.57080) CCODE(-nan(ind))
atan2(+2.00000,+0.00000)= Matlab(+1.57080) C(+1.57080) CCODE(-nan(ind))
atan2(-2.00000,+1.00000)= Matlab(-1.10715) C(-1.10715) CCODE(-nan(ind))
atan2(-1.00000,+1.00000)= Matlab(-0.78540) C(-0.78540) CCODE(-nan(ind))
atan2(+0.00000,+1.00000)= Matlab(+0.00000) C(+0.00000) CCODE(-nan(ind))
atan2(+1.00000,+1.00000)= Matlab(+0.78540) C(+0.78540) CCODE(-nan(ind))
atan2(+2.00000,+1.00000)= Matlab(+1.10715) C(+1.10715) CCODE(-nan(ind))
atan2(-2.00000,+2.00000)= Matlab(-0.78540) C(-0.78540) CCODE(-nan(ind))
atan2(-1.00000,+2.00000)= Matlab(-0.46365) C(-0.46365) CCODE(-nan(ind))
atan2(+0.00000,+2.00000)= Matlab(+0.00000) C(+0.00000) CCODE(-nan(ind))
atan2(+1.00000,+2.00000)= Matlab(+0.46365) C(+0.46365) CCODE(-nan(ind))
atan2(+2.00000,+2.00000)= Matlab(+0.78540) C(+0.78540) CCODE(-nan(ind))
How can I fix this? Hoping to receive a valid answer asap.
Vincenzo
0 comentarios
Respuestas (7)
Jan
el 30 de Ag. de 2017
Editada: Jan
el 30 de Ag. de 2017
There is no imaginary value for doubles in C. Then sqrt(-1.0) cannot be resolved with anything but NaN.
You are asking for atan2 in the title, but the symbolic expression contains atan. Is this a typo?
Questions for the MathWorks:
This is the public forum. If you want to ask MathWorks, use the "Contact Us" button on this page.
0 comentarios
Vincenzo Calabro
el 30 de Ag. de 2017
Editada: Vincenzo Calabro
el 30 de Ag. de 2017
2 comentarios
Karan Gill
el 30 de Ag. de 2017
As Jan mentioned, to contact MathWorks, please use the "Contact Us" button at the top right of the page.
Jan
el 30 de Ag. de 2017
@Vincenzo: At least I can confirm that
log((a * 1i + b) / abs(a * 1i + b)) * -1i
calculates atan2, but only if complex numbers are used. Now you know, why the created C code fails. I consider this information and the hint to contact MathWorks directly as useful. Please post here, what they reply. Thanks.
Christophe Glinel
el 28 de En. de 2019
I've the same issue with Matlab R2015b, is there is a fix now with the latest version ?
0 comentarios
Vincenzo Calabrò
el 28 de En. de 2019
Editada: Vincenzo Calabrò
el 28 de En. de 2019
to the best of my knowledge the bug is still there. you should use a different code generator to avoid this issue. check for example this third party addon:
1 comentario
Vincenzo Calabrò
el 28 de En. de 2019
yes it is a cloud service to generate code from symbolic toolbox into C/C++/C#/Java/Python/Labview.
go to: cybertronics.cloud
to get more info and examples.
1 comentario
Christophe Glinel
el 29 de En. de 2019
I got an answer from mathworks support and it is fixed in matlab 2018a
Vincenzo Calabrò
el 29 de En. de 2019
oh finally :)
good to know. btw sym2code offers more possibilities ;)
0 comentarios
Ver también
Categorías
Más información sobre Signal Integrity Kits for Industry Standards en Help Center y File Exchange.
Productos
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!