Переменная частота дискретизации в OpenModelica

Я имею в виду этот пост:

альтернатива функции выборки с изменяющимся диапазоном выборки

Я хочу измерить среднеквадратичное значение (или среднее значение) с переменной частотой дискретизации, которую я могу подавать в качестве входного сигнала.

Предлагаемый способ, который почти соответствует моим потребностям, следующий:

model RMS
  constant Real f_max = 2*2*asin(1.0);
  constant Real f = 1+abs(2*asin(time));
  Real signal = sin(time);
  Real rms = if time < f then (if time < 1e-10 then signal else sqrt(i_sq / time)) else sqrt(i_sq_f / f);
  Real i_sq(start=0, fixed=true);
  Real i_sq_f = i_sq - delay(i_sq, f, f_max);
equation
  der(i_sq) = signal^2;
end RMS;

Это вызывает ошибку: компонент f изменчивости CONST имеет привязку 1.0 + abs (2.0 * asin (время)) более высокой вариабельности VAR.

Есть ли способ решить эту проблему и подать частоту как реальное входное значение?


person H Bode    schedule 23.06.2020    source источник


Ответы (3)


Выражение для f зависит от времени, но f объявлено как constant.

Просто замените constant Real f = ... на input Real f = .... Затем вы можете указать f снаружи модели, если хотите.

person Rene Just Nielsen    schedule 23.06.2020

Основная проблема с кодом заключается в том, что time - это переменная, то есть она меняет свое значение с течением времени. Это соответствует выражению непрерывного времени в спецификации языка Modelica (см. Главу 3.8). Переменная может быть присвоена только переменной с такой же или большей изменчивостью. Следовательно, невозможно присвоить что-либо, вычисленное из time, константе, так как результат не будет постоянным. Таким образом, удаление constant в определении f решит проблему.

Замена constant на input в определении f заставит инструмент ожидать, что f будет предоставлен извне. В качестве альтернативы вы можете использовать Modelica.Blocks.Interfaces.RealInput.

Также f_max звучит скорее как parameter, чем как _12 _...

Кроме того, если время станет больше 1, возникнет проблема с «asin (время)». Но это другая история ...

person Markus A.    schedule 23.06.2020

Нашел решение, в приведенном выше примере возникли проблемы. Один с постоянным реальным f, другой с постоянным реальным f_max, а в положениях, где требовалась разница во времени, вместо этого использовалась частота.

Ниже приводится рабочий блок

model RMS
  constant Real f_max = 10000;
Modelica.Blocks.Interfaces.RealInput f annotation(
    Placement(visible = true, transformation(origin = {0, 106}, extent = {{-20, -20}, {20, 20}}, rotation = -90), iconTransformation(origin = {0, 106}, extent = {{-20, -20}, {20, 20}}, rotation = -90))); 
 Modelica.Blocks.Interfaces.RealInput signal annotation(
    Placement(visible = true, transformation(origin = {-108, 0}, extent = {{-20, -20}, {20, 20}}, rotation = 0), iconTransformation(origin = {-108, 0}, extent = {{-20, -20}, {20, 20}}, rotation = 0)));
  Real dt = 1/f;
  Real rms = if time < dt then (if time < 1e-10 then signal else sqrt(i_sq / time)) else sqrt(i_sq_f / dt);
  Real i_sq(start=0, fixed=true);  
  Real testi = delay(i_sq, dt, f_max);
  Real i_sq_f = i_sq - delay(i_sq, dt, f_max);
Modelica.Blocks.Interfaces.RealOutput y annotation(
    Placement(visible = true, transformation(origin = {110, 0}, extent = {{-10, -10}, {10, 10}}, rotation = 0), iconTransformation(origin = {110, 0}, extent = {{-10, -10}, {10, 10}}, rotation = 0)));
equation
  der(i_sq) = signal^2;
  y = rms;
end RMS;

Изменить: размер шага моделирования должен быть больше, чем время в первом условии if. В противном случае эта программа все равно может выдавать ошибки (деление на 0)

person H Bode    schedule 23.06.2020