Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Test cases for Complex operator record support in MARCO #8

Open
casella opened this issue Nov 4, 2023 · 7 comments
Open

Test cases for Complex operator record support in MARCO #8

casella opened this issue Nov 4, 2023 · 7 comments
Assignees

Comments

@casella
Copy link
Contributor

casella commented Nov 4, 2023

Here is a bunch of tests for the support of the Complex operator record in MARCO, borrowed from OpenModelica/OpenModelica#11504:

package ComplexTest
  model T01
    parameter Complex z1 = Complex(1);
    parameter Complex z2 = Complex(0, 1);
    parameter Complex z3 = z1 + z2;
    Complex z4, z5;
  equation
    z4 = z1*z2;
    z5 = z1/z2;
  end T01;

  model T02
    Complex z1 = Complex(1);
    Complex z2 = Complex(0, 1);
    Complex z3, z4, z5;
  equation
    z3 = z1 + z2;
    z4 = z1*z2;
    z5 = z1/z2;
  end T02;
  
  model T03
    Complex z1;
    Complex z2;
    Complex z3, z4, z5;
  equation
    z1 = Complex(1);
    z2 = Complex(0, 1);
    z3 = z1 + z2;
    z4 = z1*z2;
    z5 = z1/z2;
  end T03;
  
  model T04
    Complex z1, z2, z3, z4, z5;
  equation
    z1 = Complex(time,0);
    z2 = Complex(0,1);
    z3 = z1 + z2;
    z4 = z1*z2;
    z5 = z1/z2;
  end T04; 
  
  model T05
    Complex z1;
  equation
    z1  = Complex(time,0);
  end T05;

  model T06
    Complex z1 = Complex(time,0);
  equation
  end T06;

  model T07
    Complex z1 = Complex(time,0);
    Complex z2 = Complex(0, 1);
    Complex z3, z4, z5;
  equation
    z3 = z1 + z2;
    z4 = z1*z2;
    z5 = z1/z2;
  end T07;
  
  model T08
    parameter Real v_re_start = 1;
    parameter Real v_im_start = 0;
    parameter Real i_re_start = 1;
    parameter Real i_im_start = -0.3;
    parameter Complex Z = Complex(0.03,0.1);
    Complex v0 = Complex(1);
    Complex v(re(start = v_re_start), im(start = v_im_start));
    Complex i(re(start = i_re_start), im(start = i_im_start));
  equation
    v = v0 - Z*i;
    v*Modelica.ComplexMath.conj(i) = Complex(1,0.2);
  end T08;
  
  model T09
    parameter Real v_re_start = 1;
    parameter Real v_im_start = 0;
    parameter Real i_re_start = 1;
    parameter Real i_im_start = -0.3;
    parameter Complex Z = Complex(0.03,0.1);
    Complex v0 = Complex(1);
    Complex v(re(start = v_re_start), im(start = v_im_start));
    Complex i(re(start = i_re_start), im(start = i_im_start));
    Real P,Q;
  equation
    v = v0 - Z*i;
    P = 1 + 0.1*time;
    Q = 0.2 + 0.1*time;
    v*Modelica.ComplexMath.conj(i) = Complex(P, Q);
  end T09;
  model T10
    Real a = 1;
    Real b = 1;
    Complex z(re = a, im = b);
  end T10;

annotation(uses(Complex));
end ComplexTest;

@mscuttari, can you please report on the current status with the latest development version of the compiler?

@mscuttari
Copy link
Member

mscuttari commented Nov 5, 2023

  • T01 compiles and simulates successfully. The output of the simulation is the following:
"time","z1.im","z1.re","z2.im","z2.re","z3.im","z3.re","z4.im","z4.re","z5.im","z5.re"
0.000000000,0.000000000,1.000000000,1.000000000,0.000000000,1.000000000,1.000000000,1.000000000,0.000000000,-1.000000000,0.000000000
0.100000000,0.000000000,1.000000000,1.000000000,0.000000000,1.000000000,1.000000000,1.000000000,0.000000000,-1.000000000,0.000000000
0.200000000,0.000000000,1.000000000,1.000000000,0.000000000,1.000000000,1.000000000,1.000000000,0.000000000,-1.000000000,0.000000000
...
9.800000000,0.000000000,1.000000000,1.000000000,0.000000000,1.000000000,1.000000000,1.000000000,0.000000000,-1.000000000,0.000000000
9.900000000,0.000000000,1.000000000,1.000000000,0.000000000,1.000000000,1.000000000,1.000000000,0.000000000,-1.000000000,0.000000000
10.000000000,0.000000000,1.000000000,1.000000000,0.000000000,1.000000000,1.000000000,1.000000000,0.000000000,-1.000000000,0.000000000
  • T02 compiles and simulates successfully. The output of the simulation is the following:
"time","z1.im","z1.re","z2.im","z2.re","z3.im","z3.re","z4.im","z4.re","z5.im","z5.re"
0.000000000,0.000000000,1.000000000,1.000000000,0.000000000,1.000000000,1.000000000,1.000000000,0.000000000,-1.000000000,0.000000000
0.100000000,0.000000000,1.000000000,1.000000000,0.000000000,1.000000000,1.000000000,1.000000000,0.000000000,-1.000000000,0.000000000
0.200000000,0.000000000,1.000000000,1.000000000,0.000000000,1.000000000,1.000000000,1.000000000,0.000000000,-1.000000000,0.000000000
...
9.800000000,0.000000000,1.000000000,1.000000000,0.000000000,1.000000000,1.000000000,1.000000000,0.000000000,-1.000000000,0.000000000
9.900000000,0.000000000,1.000000000,1.000000000,0.000000000,1.000000000,1.000000000,1.000000000,0.000000000,-1.000000000,0.000000000
10.000000000,0.000000000,1.000000000,1.000000000,0.000000000,1.000000000,1.000000000,1.000000000,0.000000000,-1.000000000,0.000000000
  • T03 compiles and simulates successfully. The output of the simulation is the following:
0.000000000,0.000000000,1.000000000,1.000000000,0.000000000,1.000000000,1.000000000,1.000000000,0.000000000,-1.000000000,0.000000000
0.100000000,0.000000000,1.000000000,1.000000000,0.000000000,1.000000000,1.000000000,1.000000000,0.000000000,-1.000000000,0.000000000
0.200000000,0.000000000,1.000000000,1.000000000,0.000000000,1.000000000,1.000000000,1.000000000,0.000000000,-1.000000000,0.000000000
...
9.800000000,0.000000000,1.000000000,1.000000000,0.000000000,1.000000000,1.000000000,1.000000000,0.000000000,-1.000000000,0.000000000
9.900000000,0.000000000,1.000000000,1.000000000,0.000000000,1.000000000,1.000000000,1.000000000,0.000000000,-1.000000000,0.000000000
10.000000000,0.000000000,1.000000000,1.000000000,0.000000000,1.000000000,1.000000000,1.000000000,0.000000000,-1.000000000,0.000000000
  • T04 compiles and simulates successfully. The output of the simulation is the following:
"time","z1.im","z1.re","z2.im","z2.re","z3.im","z3.re","z4.im","z4.re","z5.im","z5.re"
0.000000000,0.000000000,0.000000000,1.000000000,0.000000000,1.000000000,0.000000000,0.000000000,0.000000000,0.000000000,0.000000000
0.100000000,0.000000000,0.100000000,1.000000000,0.000000000,1.000000000,0.100000000,0.100000000,0.000000000,-0.100000000,0.000000000
0.200000000,0.000000000,0.200000000,1.000000000,0.000000000,1.000000000,0.200000000,0.200000000,0.000000000,-0.200000000,0.000000000
...
9.800000000,0.000000000,9.800000000,1.000000000,0.000000000,1.000000000,9.800000000,9.800000000,0.000000000,-9.800000000,0.000000000
9.900000000,0.000000000,9.900000000,1.000000000,0.000000000,1.000000000,9.900000000,9.900000000,0.000000000,-9.900000000,0.000000000
10.000000000,0.000000000,10.000000000,1.000000000,0.000000000,1.000000000,10.000000000,10.000000000,0.000000000,-10.000000000,0.000000000

  • T05 compiles and simulates successfully. The output of the simulation is the following:
"time","z1.im","z1.re"
0.000000000,0.000000000,0.000000000
0.100000000,0.000000000,0.100000000
0.200000000,0.000000000,0.200000000
...
9.800000000,0.000000000,9.800000000
9.900000000,0.000000000,9.900000000
10.000000000,0.000000000,10.000000000
  • T06 compiles and simulates successfully. The output of the simulation is the following:
"time","z1.im","z1.re"
0.000000000,0.000000000,0.000000000
0.100000000,0.000000000,0.100000000
0.200000000,0.000000000,0.200000000
...
9.800000000,0.000000000,9.800000000
9.900000000,0.000000000,9.900000000
10.000000000,0.000000000,10.000000000
  • T07 compiles and simulates successfully. The output of the simulation is the following:
"time","z1.im","z1.re","z2.im","z2.re","z3.im","z3.re","z4.im","z4.re","z5.im","z5.re"
0.000000000,0.000000000,0.000000000,1.000000000,0.000000000,1.000000000,0.000000000,0.000000000,0.000000000,0.000000000,0.000000000
0.100000000,0.000000000,0.100000000,1.000000000,0.000000000,1.000000000,0.100000000,0.100000000,0.000000000,-0.100000000,0.000000000
0.200000000,0.000000000,0.200000000,1.000000000,0.000000000,1.000000000,0.200000000,0.200000000,0.000000000,-0.200000000,0.000000000
...
9.800000000,0.000000000,9.800000000,1.000000000,0.000000000,1.000000000,9.800000000,9.800000000,0.000000000,-9.800000000,0.000000000
9.900000000,0.000000000,9.900000000,1.000000000,0.000000000,1.000000000,9.900000000,9.900000000,0.000000000,-9.900000000,0.000000000
10.000000000,0.000000000,10.000000000,1.000000000,0.000000000,1.000000000,10.000000000,10.000000000,0.000000000,-10.000000000,0.000000000
  • T08 currently does not link due to problems with the SUNDIALS libraries on my local machine. I will investigate.
  • T09 has the same problem of T08

@mscuttari
Copy link
Member

T08 (and possibly T09) also leads to problems during the equation explicitation phase. However, the record expansion and function inlining work correctly, so this is not a problem strictly related to record handling.

@casella
Copy link
Contributor Author

casella commented Nov 5, 2023

Very good news, the results reported for T01-T07 are indeed correct 😃

For power system models to work, we also need to get IDA to work, so that last part is also required.

@casella
Copy link
Contributor Author

casella commented Nov 9, 2023

@mscuttari I added T10 to the test cases, this is another pattern used by PowerGrids, please check that it works.

I would suggest to add the updated version of ComplexTest to the marco testsuite, so we make sure these features do not get broken.

@mscuttari
Copy link
Member

mscuttari commented Dec 12, 2023

Regarding the problems about T08 using IDA, I've been checking the Jacobian matrix computed by MARCO and it is indeed coherent with its input data. The problem, instead, relies in OpenModelica not properly handling the start attributes:

omc Record.mo -f -i=ComplexTest.T08 -d=nonfScalarize,arrayConnect,combineSubscripts,printRecordTypes,evaluateAllParameters,vectorizeBindings --showStructuralAnnotations

model 'ComplexTest.T08'
function 'Complex.\'*\'.multiply' "Multiply two complex numbers"
  input 'Complex' 'c1';
  input 'Complex' 'c2';
  output 'Complex' 'c3';
algorithm
  'c3' := 'Complex.\'constructor\'.fromReal'('c1'.'re' * 'c2'.'re' - 'c1'.'im' * 'c2'.'im', 'c1'.'re' * 'c2'.'im' + 'c1'.'im' * 'c2'.'re');
  annotation(Inline = true);
end 'Complex.\'*\'.multiply';

function 'Complex.\'-\'.subtract' "Subtract two complex numbers"
  input 'Complex' 'c1';
  input 'Complex' 'c2';
  output 'Complex' 'c3';
algorithm
  'c3' := 'Complex.\'constructor\'.fromReal'('c1'.'re' - 'c2'.'re', 'c1'.'im' - 'c2'.'im');
  annotation(Inline = true);
end 'Complex.\'-\'.subtract';

function 'Complex.\'constructor\'.fromReal' "Construct Complex from Real"
  input Real 're';
  input Real 'im' = 0.0;
  output 'Complex' 'result';
algorithm
  annotation(Inline = true);
end 'Complex.\'constructor\'.fromReal';

function 'Modelica.ComplexMath.conj' "Conjugate of complex number"
  input 'Complex' 'c1';
  output 'Complex' 'c2';
algorithm
  'c2' := 'Complex.\'constructor\'.fromReal'('c1'.'re', -'c1'.'im');
  annotation(Inline = true);
end 'Modelica.ComplexMath.conj';

record 'Complex'
  parameter Real 're';
  parameter Real 'im';
end 'Complex';

  parameter 'Complex' 'Z' = 'Complex'(0.03, 0.1);
  'Complex' 'v0' = 'Complex'(1.0, 0.0);
  'Complex' 'v';
  'Complex' 'i';
equation
  'v' = 'Complex.\'-\'.subtract'('v0', 'Complex.\'*\'.multiply'('Complex'(0.03, 0.1), 'i'));
  'Complex.\'*\'.multiply'('v', 'Modelica.ComplexMath.conj'('i')) = 'Complex'(1.0, 0.2);
end 'ComplexTest.T08';

Notice how v and i don't have start values.
Because of this, the variables v.re, v.im, i.re and i.im gets initialized with the zero value and the Jacobian matrix then becomes singular.

The same happens with model T09.

@casella
Copy link
Contributor Author

casella commented Jan 8, 2024

See #12 and OpenModelica/OpenModelica#11792

@casella
Copy link
Contributor Author

casella commented May 21, 2024

I pinged Per on the OpenModelica issue, let's see if he can fix that before Michele is back from Norway.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants