9#include <dpsim-models/DP/DP_Ph1_Inductor.h>
23 auto copy = Inductor::make(name,
mLogLevel);
42 Real omega = 2. * PI * frequency;
44 (**mIntfVoltage)(0, 0) = initialSingleVoltage(1) - initialSingleVoltage(0);
45 (**mIntfCurrent)(0, 0) = (**
mIntfVoltage)(0, 0) / impedance;
47 SPDLOG_LOGGER_INFO(
mSLog,
48 "\nInductance [H]: {:s}"
49 "\nImpedance [Ohm]: {:s}",
51 Logger::complexToString(impedance));
52 SPDLOG_LOGGER_INFO(
mSLog,
53 "\n--- Initialization from powerflow ---"
54 "\nVoltage across: {:s}"
56 "\nTerminal 0 voltage: {:s}"
57 "\nTerminal 1 voltage: {:s}"
58 "\n--- Initialization from powerflow finished ---",
61 Logger::phasorToString(initialSingleVoltage(0)),
62 Logger::phasorToString(initialSingleVoltage(1)));
67void DP::Ph1::Inductor::initVars(Real timeStep) {
68 for (UInt freq = 0; freq < mNumFreqs; freq++) {
69 Real a = timeStep / (2. * **mInductance);
70 Real b = timeStep * 2. * PI * mFrequencies(freq, 0) / 2.;
72 Real equivCondReal = a / (1. + b * b);
73 Real equivCondImag = -a * b / (1. + b * b);
74 mEquivCond(freq, 0) = {equivCondReal, equivCondImag};
75 Real preCurrFracReal = (1. - b * b) / (1. + b * b);
76 Real preCurrFracImag = (-2. * b) / (1. + b * b);
77 mPrevCurrFac(freq, 0) = {preCurrFracReal, preCurrFracImag};
80 mEquivCurrent(freq, 0) = mEquivCond(freq, 0) * (**mIntfVoltage)(0, freq) +
81 mPrevCurrFac(freq, 0) * (**mIntfCurrent)(0, freq);
82 (**mIntfCurrent)(0, freq) =
83 mEquivCond(freq, 0) * (**mIntfVoltage)(0, freq) +
84 mEquivCurrent(freq, 0);
89 Attribute<Matrix>::Ptr leftVector) {
93 SPDLOG_LOGGER_INFO(
mSLog,
94 "\n--- MNA initialization ---"
95 "\nInitial voltage {:s}"
96 "\nInitial current {:s}"
97 "\nEquiv. current {:s}"
98 "\n--- MNA initialization finished ---",
104void DP::Ph1::Inductor::mnaCompInitializeHarm(
105 Real omega, Real timeStep,
106 std::vector<Attribute<Matrix>::Ptr> leftVectors) {
107 updateMatrixNodeIndices();
111 mMnaTasks.push_back(std::make_shared<MnaPreStepHarm>(*
this));
112 mMnaTasks.push_back(std::make_shared<MnaPostStepHarm>(*
this, leftVectors));
113 **mRightVector = Matrix::Zero(leftVectors[0]->get().rows(), mNumFreqs);
117 SparseMatrixRow &systemMatrix) {
118 for (UInt freq = 0; freq <
mNumFreqs; freq++) {
119 MNAStampUtils::stampAdmittance(
120 mEquivCond(freq, 0), systemMatrix, matrixNodeIndex(0),
121 matrixNodeIndex(1), terminalNotGrounded(0), terminalNotGrounded(1),
126void DP::Ph1::Inductor::mnaCompApplySystemMatrixStampHarm(
127 SparseMatrixRow &systemMatrix, Int freqIdx) {
128 MNAStampUtils::stampAdmittance(mEquivCond(freqIdx, 0), systemMatrix,
129 matrixNodeIndex(0), matrixNodeIndex(1),
130 terminalNotGrounded(0), terminalNotGrounded(1),
135 for (UInt freq = 0; freq <
mNumFreqs; freq++) {
140 if (terminalNotGrounded(0))
141 Math::setVectorElement(rightVector, matrixNodeIndex(0),
143 if (terminalNotGrounded(1))
144 Math::setVectorElement(rightVector, matrixNodeIndex(1),
147 SPDLOG_LOGGER_DEBUG(
mSLog,
"MNA EquivCurrent {:s}",
149 if (terminalNotGrounded(0))
150 SPDLOG_LOGGER_DEBUG(
mSLog,
"Add {:s} to source vector at {:d}",
153 if (terminalNotGrounded(1))
154 SPDLOG_LOGGER_DEBUG(
mSLog,
"Add {:s} to source vector at {:d}",
160void DP::Ph1::Inductor::mnaCompApplyRightSideVectorStampHarm(
161 Matrix &rightVector) {
162 for (UInt freq = 0; freq < mNumFreqs; freq++) {
164 mEquivCurrent(freq, 0) = mEquivCond(freq, 0) * (**mIntfVoltage)(0, freq) +
165 mPrevCurrFac(freq, 0) * (**mIntfCurrent)(0, freq);
167 if (terminalNotGrounded(0))
168 Math::setVectorElement(rightVector, matrixNodeIndex(0),
169 mEquivCurrent(freq, 0), 1, 0, freq);
170 if (terminalNotGrounded(1))
171 Math::setVectorElement(rightVector, matrixNodeIndex(1),
172 -mEquivCurrent(freq, 0), 1, 0, freq);
177 AttributeBase::List &prevStepDependencies,
178 AttributeBase::List &attributeDependencies,
179 AttributeBase::List &modifiedAttributes) {
191 AttributeBase::List &prevStepDependencies,
192 AttributeBase::List &attributeDependencies,
193 AttributeBase::List &modifiedAttributes,
194 Attribute<Matrix>::Ptr &leftVector) {
195 attributeDependencies.push_back(leftVector);
201 Attribute<Matrix>::Ptr &leftVector) {
206void DP::Ph1::Inductor::MnaPreStepHarm::execute(Real time, Int timeStepCount) {
207 mInductor.mnaCompApplyRightSideVectorStampHarm(**mInductor.mRightVector);
210void DP::Ph1::Inductor::MnaPostStepHarm::execute(Real time, Int timeStepCount) {
211 for (UInt freq = 0; freq < mInductor.mNumFreqs; freq++)
212 mInductor.mnaCompUpdateVoltageHarm(**mLeftVectors[freq], freq);
213 mInductor.mnaCompUpdateCurrentHarm();
218 for (UInt freq = 0; freq <
mNumFreqs; freq++) {
219 (**mIntfVoltage)(0, freq) = 0;
220 if (terminalNotGrounded(1))
221 (**mIntfVoltage)(0, freq) = Math::complexFromVectorElement(
222 leftVector, matrixNodeIndex(1),
mNumFreqs, freq);
223 if (terminalNotGrounded(0))
224 (**mIntfVoltage)(0, freq) =
226 Math::complexFromVectorElement(leftVector, matrixNodeIndex(0),
229 SPDLOG_LOGGER_DEBUG(
mSLog,
"Voltage {:s}",
234void DP::Ph1::Inductor::mnaCompUpdateVoltageHarm(
const Matrix &leftVector,
237 (**mIntfVoltage)(0, freqIdx) = 0;
238 if (terminalNotGrounded(1))
239 (**mIntfVoltage)(0, freqIdx) =
240 Math::complexFromVectorElement(leftVector, matrixNodeIndex(1));
241 if (terminalNotGrounded(0))
242 (**mIntfVoltage)(0, freqIdx) =
243 (**mIntfVoltage)(0, freqIdx) -
244 Math::complexFromVectorElement(leftVector, matrixNodeIndex(0));
246 SPDLOG_LOGGER_DEBUG(mSLog,
"Voltage {:s}",
247 Logger::phasorToString((**mIntfVoltage)(0, freqIdx)));
251 for (UInt freq = 0; freq <
mNumFreqs; freq++) {
252 (**mIntfCurrent)(0, freq) =
253 mEquivCond(freq, 0) * (**mIntfVoltage)(0, freq) +
255 SPDLOG_LOGGER_DEBUG(
mSLog,
"Current {:s}",
260void DP::Ph1::Inductor::mnaCompUpdateCurrentHarm() {
261 for (UInt freq = 0; freq < mNumFreqs; freq++) {
262 (**mIntfCurrent)(0, freq) =
263 mEquivCond(freq, 0) * (**mIntfVoltage)(0, freq) +
264 mEquivCurrent(freq, 0);
265 SPDLOG_LOGGER_DEBUG(mSLog,
"Current {:s}",
266 Logger::phasorToString((**mIntfCurrent)(0, freq)));
271void DP::Ph1::Inductor::mnaTearInitialize(Real omega, Real timeStep) {
275void DP::Ph1::Inductor::mnaTearApplyMatrixStamp(SparseMatrixRow &tearMatrix) {
276 Math::addToMatrixElement(tearMatrix, mTearIdx, mTearIdx,
277 1. / mEquivCond(0, 0));
280void DP::Ph1::Inductor::mnaTearApplyVoltageStamp(Matrix &voltageVector) {
281 mEquivCurrent(0, 0) = mEquivCond(0, 0) * (**mIntfVoltage)(0, 0) +
282 mPrevCurrFac(0, 0) * (**mIntfCurrent)(0, 0);
283 Math::addToVectorElement(voltageVector, mTearIdx,
284 mEquivCurrent(0, 0) / mEquivCond(0, 0));
287void DP::Ph1::Inductor::mnaTearPostStep(Complex voltage, Complex current) {
288 (**mIntfVoltage)(0, 0) = voltage;
289 (**mIntfCurrent)(0, 0) = mEquivCond(0, 0) * voltage + mEquivCurrent(0, 0);
const CPS::Attribute< Real >::Ptr mInductance
Inductance [H].
MatrixComp mEquivCond
Equivalent conductance for harmonics [S].
void mnaCompUpdateCurrent(const Matrix &leftVector) override
Update interface current from MNA system results.
void mnaCompAddPostStepDependencies(AttributeBase::List &prevStepDependencies, AttributeBase::List &attributeDependencies, AttributeBase::List &modifiedAttributes, Attribute< Matrix >::Ptr &leftVector) override
Add MNA post step dependencies.
SimPowerComp< Complex >::Ptr clone(String name) override
Return new instance with the same parameters.
MatrixComp mEquivCurrent
DC equivalent current source for harmonics [A].
void mnaCompAddPreStepDependencies(AttributeBase::List &prevStepDependencies, AttributeBase::List &attributeDependencies, AttributeBase::List &modifiedAttributes) override
Add MNA pre step dependencies.
void mnaCompInitialize(Real omega, Real timeStep, Attribute< Matrix >::Ptr leftVector) override
Initializes MNA specific variables.
void mnaCompUpdateVoltage(const Matrix &leftVector) override
Update interface voltage from MNA system results.
Complex getMNAConductance() const
Return single-frequency MNA companion conductance.
void mnaCompPostStep(Real time, Int timeStepCount, Attribute< Matrix >::Ptr &leftVector) override
MNA post step operations.
MatrixComp mPrevCurrFac
Coefficient in front of previous current value for harmonics.
void mnaCompApplyRightSideVectorStamp(Matrix &rightVector) override
Stamps right side (source) vector.
void initializeFromNodesAndTerminals(Real frequency) override
Initializes states from power flow data.
void initialize(Matrix frequencies) override
Initializes state variables considering the number of frequencies.
void mnaCompPreStep(Real time, Int timeStepCount) override
MNA pre step operations.
void mnaCompApplySystemMatrixStamp(SparseMatrixRow &systemMatrix) override
Stamps system matrix.
Inductor(String uid, String name, Logger::Level logLevel=Logger::Level::off)
Defines UID, name and log level.
String uid()
Returns unique id.
AttributeList::Ptr mAttributes
Attribute List.
void mnaUpdateCurrent(const Matrix &leftVector) final
void mnaUpdateVoltage(const Matrix &leftVector) final
MNASimPowerComp(String uid, String name, Bool hasPreStep, Bool hasPostStep, Logger::Level logLevel)
Attribute< Matrix >::Ptr mRightVector
void mnaApplyRightSideVectorStamp(Matrix &rightVector) final
const Attribute< MatrixVar< Complex > >::Ptr mIntfCurrent
virtual void initialize(Matrix frequencies)
Initialize components with correct network frequencies.
const Attribute< MatrixVar< Complex > >::Ptr mIntfVoltage
void updateMatrixNodeIndices()
Logger::Level mLogLevel
Component logger control for internal variables.
Logger::Log mSLog
Component logger.