Skip to content

Commit c60f99a

Browse files
Merge pull request #373 from ven-k/vkb/fix-diode-tests
Fix the diode tests + Refactor with `@mtkmodel`
2 parents b5b01b4 + 9102fae commit c60f99a

File tree

2 files changed

+84
-85
lines changed

2 files changed

+84
-85
lines changed

src/Electrical/Analog/ideal_components.jl

+10-11
Original file line numberDiff line numberDiff line change
@@ -273,22 +273,21 @@ Ideal diode based on the Shockley diode equation.
273273
- See [OnePort](@ref)
274274
275275
# Connectors
276-
276+
277277
- `p` Positive pin
278278
- `n` Negative pin
279279
280280
# Parameters
281-
281+
282282
- `Is`: [`A`] Saturation current
283283
- `n`: Ideality factor
284284
- `T`: [K] Ambient temperature
285285
"""
286286
@mtkmodel Diode begin
287-
begin
287+
@constants begin
288288
k = 1.380649e-23 # Boltzmann constant (J/K)
289289
q = 1.602176634e-19 # Elementary charge (C)
290290
end
291-
292291
@extend v, i = oneport = OnePort(; v = 0.0)
293292
@parameters begin
294293
Is = 1e-6, [description = "Saturation current (A)"]
@@ -310,13 +309,13 @@ Temperature dependent diode based on the Shockley diode equation.
310309
- See [OnePort](@ref)
311310
312311
# Connectors
313-
312+
314313
- `p` Positive pin
315314
- `n` Negative pin
316315
- `port` [HeatPort](@ref) Heat port to model the temperature dependency
317316
318317
# Parameters:
319-
318+
320319
- `Is`: [`A`] Saturation current
321320
- `n`: Ideality factor
322321
"""
@@ -349,13 +348,13 @@ end
349348
350349
Variable resistor with optional temperature dependency.
351350
352-
The total resistance R ∈ [R_const, R_const + R_ref], where pos is the
353-
position of the wiper and R_ref is the variable resistance between p and n.
351+
The total resistance R ∈ [R_const, R_const + R_ref], where pos is the
352+
position of the wiper and R_ref is the variable resistance between p and n.
354353
The total resistance is then:
355354
356355
R = R_const + pos * R_ref
357356
358-
If T_dep is true, then R also depends on the temperature of the heat port with
357+
If T_dep is true, then R also depends on the temperature of the heat port with
359358
temperature coefficient alpha. The total resistance is then:
360359
361360
R = R_const + pos * R_ref * (1 + alpha * (port.T - T_ref))
@@ -367,14 +366,14 @@ R = R_const + pos * R_ref * (1 + alpha * (port.T - T_ref))
367366
- `R(t)`: Resistance
368367
369368
# Connectors
370-
369+
371370
- `p` Positive pin
372371
- `n` Negative pin
373372
- `position` RealInput to set the position of the wiper
374373
- `port` [HeatPort](@ref) Heat port to model the temperature dependency
375374
376375
# Parameters
377-
376+
378377
- `R_ref`: [`Ω`] Resistance at temperature T_ref when fully closed (pos=1.0)
379378
- `T_ref`: [K] Reference temperature
380379
- `R_const`: [`Ω`] Constant resistance between p and n

test/Electrical/analog.jl

+74-74
Original file line numberDiff line numberDiff line change
@@ -375,45 +375,45 @@ end
375375
end
376376

377377
@testset "Diode component test" begin
378-
# Parameter values
379-
R = 1.0
380-
C = 1.0
381-
V = 10.0
382-
n = 1.0
383-
Is = 1e-3
384-
f = 1.0
385-
386-
# Components
387-
@named resistor = Resistor(R = R)
388-
@named capacitor = Capacitor(C = C, v = 0.0)
389-
@named source = Voltage()
390-
@named diode = Diode(n = n, Is = Is)
391-
@named ac = Sine(frequency = f, amplitude = V)
392-
@named ground = Ground()
393-
394-
# Connections
395-
connections = [connect(ac.output, source.V)
396-
connect(source.p, diode.p)
397-
connect(diode.n, resistor.p)
398-
connect(resistor.n, capacitor.p)
399-
connect(capacitor.n, source.n, ground.g)]
378+
@mtkmodel DiodeTest begin
379+
@parameters begin
380+
R = 1.0
381+
C = 1.0
382+
V = 10.0
383+
n = 1.0
384+
Is = 1e-3
385+
f = 1.0
386+
end
387+
@components begin
388+
resistor = Resistor(R = R)
389+
capacitor = Capacitor(C = C, v = 0.0)
390+
source = Voltage()
391+
diode = Diode(n = n, Is = Is)
392+
ac = Sine(frequency = f, amplitude = V)
393+
ground = Ground()
394+
end
395+
@equations begin
396+
connect(ac.output, source.V)
397+
connect(source.p, diode.p)
398+
connect(diode.n, resistor.p)
399+
connect(resistor.n, capacitor.p)
400+
connect(capacitor.n, source.n, ground.g)
401+
end
402+
end
400403

401-
# Model
402-
@named model = ODESystem(connections, t;
403-
systems = [resistor, capacitor, source, diode, ac, ground])
404-
sys = structural_simplify(model)
404+
@mtkbuild sys = DiodeTest()
405405
prob = ODEProblem(sys, Pair[], (0.0, 10.0))
406-
sol = solve(prob)
406+
sol = solve(prob, Rodas4())
407407

408408
# Extract solutions for testing
409-
diode_voltage = sol[diode.v]
410-
diode_current = sol[diode.i]
411-
resistor_current = sol[resistor.i]
412-
capacitor_voltage = sol[capacitor.v]
409+
diode_voltage = sol[sys.diode.v]
410+
diode_current = sol[sys.diode.i]
411+
resistor_current = sol[sys.resistor.i]
412+
capacitor_voltage = sol[sys.capacitor.v]
413413

414414
# Tests
415-
@test all(diode_current .>= -Is)
416-
@test capacitor_voltage[end].V rtol=3e-1
415+
@test all(diode_current .>= -1e-3)
416+
@test capacitor_voltage[end].8.26 rtol=3e-1
417417

418418
# For visual inspection
419419
# plt = plot(sol; vars = [diode.i, resistor.i, capacitor.v],
@@ -424,53 +424,53 @@ end
424424
end
425425

426426
@testset "HeatingDiode component test" begin
427-
# Parameter values
428-
R = 1.0
429-
C = 1.0
430-
V = 10.0
431-
T = 300.0 # Ambient temperature in Kelvin
432-
n = 2.0
433-
Is = 1e-6
434-
f = 1.0
435-
436-
# Components
437-
@named resistor = Resistor(R = R)
438-
@named capacitor = Capacitor(C = C, v = 0.0)
439-
@named source = Voltage()
440-
@named heating_diode = HeatingDiode(n = n, Is = Is)
441-
@named ac = Sine(frequency = f, amplitude = V)
442-
@named ground = Ground()
443-
@named temp = FixedTemperature(T = T)
444-
445-
# Connections
446-
connections = [connect(ac.output, source.V),
447-
connect(source.p, heating_diode.p),
448-
connect(heating_diode.n, resistor.p),
449-
connect(resistor.n, capacitor.p),
450-
connect(capacitor.n, ground.g),
451-
connect(source.n, ground.g),
452-
connect(temp.port, heating_diode.port)]
453-
454-
# Model
455-
@named model = ODESystem(connections, t;
456-
systems = [resistor, capacitor, source, heating_diode, ac, ground, temp])
457-
sys = structural_simplify(model)
427+
@mtkmodel HeatingDiodeTest begin
428+
@parameters begin
429+
R = 1.0
430+
C = 1.0
431+
V = 10.0
432+
T = 300.0 # Ambient temperature in Kelvin
433+
n = 2.0
434+
Is = 1e-6
435+
f = 1.0
436+
end
437+
@components begin
438+
resistor = Resistor(R = R)
439+
capacitor = Capacitor(C = C, v = 0.0)
440+
source = Voltage()
441+
heating_diode = HeatingDiode(n = n, Is = Is)
442+
ac = Sine(frequency = f, amplitude = V)
443+
ground = Ground()
444+
temp = FixedTemperature(T = T)
445+
end
446+
@equations begin
447+
connect(ac.output, source.V)
448+
connect(source.p, heating_diode.p)
449+
connect(heating_diode.n, resistor.p)
450+
connect(resistor.n, capacitor.p)
451+
connect(capacitor.n, ground.g)
452+
connect(source.n, ground.g)
453+
connect(temp.port, heating_diode.port)
454+
end
455+
end
456+
457+
@mtkbuild sys = HeatingDiodeTest()
458458
prob = ODEProblem(sys, Pair[], (0.0, 10.0))
459-
sol = solve(prob)
459+
sol = solve(prob, Rodas4())
460460

461461
# Extract solutions for testing
462-
diode_voltage = sol[heating_diode.v]
463-
diode_current = sol[heating_diode.i]
464-
resistor_current = sol[resistor.i]
465-
capacitor_voltage = sol[capacitor.v]
462+
diode_voltage = sol[sys.heating_diode.v]
463+
diode_current = sol[sys.heating_diode.i]
464+
resistor_current = sol[sys.resistor.i]
465+
capacitor_voltage = sol[sys.capacitor.v]
466466

467467
# Expected thermal voltage at given temperature
468468
k = 1.380649e-23 # Boltzmann constant (J/K)
469469
q = 1.602176634e-19 # Elementary charge (C)
470470

471471
# Tests
472-
@test all(diode_current .>= -Is) # Diode current should not exceed reverse saturation
473-
@test capacitor_voltage[end]V rtol=3e-1 # Final capacitor voltage close to input voltage
472+
@test all(diode_current .>= -1e-6) # Diode current should not exceed reverse saturation
473+
@test capacitor_voltage[end]7.75 rtol=3e-1 # Final capacitor voltage close to input voltage
474474

475475
# For visual inspection
476476
# plt = plot(sol; vars = [heating_diode.i, resistor.i, capacitor.v],
@@ -481,10 +481,10 @@ end
481481

482482
# Remake model with higher amb. temperature, final capacitor voltage should be lower
483483
T = 400.0
484-
model = remake(prob; p = [temp.T => T])
485-
sol = solve(model)
484+
reprob = remake(prob; p = [sys.T => T])
485+
sol = solve(reprob, Rodas4())
486486
@test SciMLBase.successful_retcode(sol)
487-
@test sol[capacitor.v][end] < capacitor_voltage[end]
487+
@test sol[sys.capacitor.v][end] < capacitor_voltage[end]
488488
end
489489

490490
@testset "VariableResistor with Temperature Dependency" begin

0 commit comments

Comments
 (0)