This repository has been archived on 2023-08-20. You can view files and clone it, but cannot push or open issues or pull requests.
yap-6.3/CLPQR/clpqr/examples/monash/rlc
vsc e5f4633c39 This commit was generated by cvs2svn to compensate for changes in r4,
which included commits to RCS files with non-trunk default branches.


git-svn-id: https://yap.svn.sf.net/svnroot/yap/trunk@5 b08c6af1-5177-4d33-ba66-4b1c6b8b522a
2001-04-09 19:54:03 +00:00

421 lines
11 KiB
Plaintext

/*
**********************************************************************
*
* CLP(R) Version 2.0 (Example Programs Release)
* (C) Copyright, March 1986, Monash University
*
**********************************************************************
*/
%
% Package for sinusoidal steady state analysis of RLC circuits.
% The two goals ?- go1 and ?- go2 analyse two
% circuits of moderate complexity.
%
circuit_solve(W, L, G, Selection) :-
get_node_vars(L, NV),
solve(W, L, NV, Handles, G),
format_print(Handles, Selection).
get_node_vars([[Comp, Num, X, Ns]|Ls], NV) :-
get_node_vars(Ls, NV1),
insert_list(Ns, NV1, NV).
get_node_vars([], []).
insert_list([N|Ns], NV1, NV3) :-
insert_list(Ns, NV1, NV2),
insert(N, NV2, NV3).
insert_list([], NV, NV).
insert(N, [[N, V, I]|NV1], [[N, V, I]|NV1]) :- !.
insert(N, [[N1, V, I]|NV1], [[N1, V, I]|NV2]) :-
insert(N, NV1, NV2).
insert(N, [], [[N, V, c(0,0)]]).
eps(0.001).
solve(W, [X|Xs], NV, [H|Hs], G) :-
addcomp(W, X, NV, NV1,H),
solve(W, Xs, NV1, Hs, G).
solve(W, [], NV, [], G) :-
!,
zero_currents(NV),
ground_nodes(NV, G).
zero_currents([[N, V, c(X,Y)]|Ls]) :-
zero(X),
zero(Y),
zero_currents(Ls).
zero_currents([]).
zero(0).
zero(X) :-
ground(X),
%printf("Is it ground: % ?\n", [X]),
eps(EPS),
X > -EPS,
X < EPS.
/* There is some redundancy setting all node current sums to zero - We only
need to some of them to zero. Setting all of them to zero can cause some
problems because of numerical instability. */
ground_nodes(Vs,[N|Ns]) :-
ground_node(Vs, N),
ground_nodes(Vs, Ns).
ground_nodes(Vs, []).
ground_node([[N, c(0,0), I]|Vs], N) :- !.
ground_node([[N1, V, I]|Vs], N) :- ground_node(Vs, N).
ground_node([], N) :- printf("Error could be: node %doesn't exist\n", [N]).
% ***** CLAUSES TO DEFINE COMPONENT CHARACTERISTICS *****
addcomp(W, [Comp2, Num, X, [N1, N2]], NV, NV2, [Comp2, Num, X, [N1, V1, I1], [N2, V2, I2]]):-
c_neg(I1, I2),
iv_reln(Comp2, I1, V, X, W),
c_add(V, V2, V1),
subst([N1, V1, Iold1], [N1, V1, Inew1], NV, NV1),
subst([N2, V2, Iold2], [N2, V2, Inew2], NV1, NV2),
c_add(I1,Iold1,Inew1),
c_add(I2,Iold2,Inew2).
% Specific current/voltage relations for the two terminal components
iv_reln(resistor, I, V, R, W) :-
c_mult(I,c(R,0),V).
iv_reln(voltage_source, I, V, V, W).
iv_reln(isource, I, V, I, W).
iv_reln(capacitor, I, V, C, W) :-
c_mult( c(0,W * C),V,I).
iv_reln(inductor, I, V, L, W) :-
c_mult(c(0,W * L),I,V).
iv_reln(connection, I, c(0,0), L, W).
iv_reln(open, c(0,0), V, L, W).
iv_reln(diode, I, V, D, W) :- diode(D, I, V).
diode(in914, c(I,0), c(V, 0)) :-
V < -100,
DV = V + 100,
I = 10*DV.
diode(in914, c(I,0), c(V, 0)) :-
V >= -100,
V < 0.6,
I = 0.001*V.
diode(in914, c(I,0), c(V, 0)) :-
V >= 0.6,
DV = V - 0.6,
I = 100*DV.
addcomp(W, [transistor, Num, X, [N1, N2, N3]], NV, NV3, [transistor, Num, X, [N1, V1, I1], [N2, V2, I2], [N3, V3, I3]]):-
transistor(X, R, Gain),
c_add(I1, I3, IT),
c_neg(I2, IT),
c_add(Vin, V2, V1),
c_mult(I1, c(R, 0), Vin),
c_mult(I1, c(Gain, 0), I3),
subst([N1, V1, Iold1], [N1, V1, Inew1], NV, NV1),
subst([N2, V2, Iold2], [N2, V2, Inew2], NV1, NV2),
subst([N3, V3, Iold3], [N3, V3, Inew3], NV2, NV3),
subst([N4, V4, Iold4], [N4, V4, Inew4], NV3, NV4),
c_add(I1,Iold1,Inew1),
c_add(I2,Iold2,Inew2),
c_add(I3,Iold3,Inew3),
c_add(I4,Iold4,Inew4).
transistor(bc108, 1000, 100).
addcomp(W, [transformer, Num, X, [N1, N2, N3, N4]], NV, NV4, [transformer, Num, X, [N1, V1, I1], [N2, V2, I2], [N3, V3, I3], [N4, V4, I4]]):-
c_neg(I1, I2),
c_neg(I3, I4),
c_add(Vin, V2, V1),
c_add(Vout, V4, V3),
c_mult(Vout, c(X, 0), Vin),
c_mult(I1, c(X, 0), I4),
subst([N1, V1, Iold1], [N1, V1, Inew1], NV, NV1),
subst([N2, V2, Iold2], [N2, V2, Inew2], NV1, NV2),
subst([N3, V3, Iold3], [N3, V3, Inew3], NV2, NV3),
subst([N4, V4, Iold4], [N4, V4, Inew4], NV3, NV4),
c_add(I1,Iold1,Inew1),
c_add(I2,Iold2,Inew2),
c_add(I3,Iold3,Inew3),
c_add(I4,Iold4,Inew4).
subst(X, Y, [X|L1], [Y|L1]) :- !.
subst(X, Y, [Z|L1], [Z|L2]) :-
subst(X,Y,L1,L2).
subst(X, Y, [], L2) :-
printf("Node list incomplete\n", []).
% ***** COMPLEX NUMBER ARITHMETIC *****
c_mult(c(Re1,Im1),c(Re2,Im2),c(Re3,Im3)) :-
Re3 = Re1*Re2 - Im1*Im2,
Im3 = Re1*Im2 + Re2*Im1.
c_add(c(Re1,Im1),c(Re2,Im2),c(Re3,Im3)) :-
Re3 = Re1 + Re2,
Im3 = Im1 + Im2.
c_neg(c(Re,Im),c(Re1,Im1)) :-
Re1 = -Re, Im1 = -Im .
c_eq(c(Re1,Im1),c(Re2,Im2)) :-
Re1 = Re2, Im1 = Im2 .
c_real(c(Re,Im),Re).
c_imag(c(Re,Im),Im).
% ****** PRINTOUT ROUTINES ******
format_print(H, []) :-
!,
all_print(H).
% If no selection is given then
% print out all nodes.
format_print(H, Selection) :-
selective_print(H, Selection).
% Otherwise print the selection.
selective_print(Ls, [N|Ns]) :-
print_nodes(Ls, N, 0),
print_comps(Ls, N),
selective_print(Ls, Ns).
selective_print(Ls, []).
print_nodes([[Comp, Num, X|Nodes]|L], N1, Heading_flag_1) :-
member(N1, Nodes),
Heading_flag_2 = Heading_flag_1 + 1,
heading(N1, Heading_flag_2),
all_print([[Comp, Num, X|Nodes]]),
print_nodes(L, N1, Heading_flag_2).
print_nodes([[Comp, Num, X|Nodes]|L], N1, Heading_flag) :-
print_nodes(L, N1, Heading_flag).
print_nodes([], N1, Heading_flag).
print_comps([[Comp, Num, X|Nodes]|L], Num) :-
all_print([[Comp, Num, X|Nodes]]),
print_comps(L, Num).
print_comps([[Comp, Num, X|Nodes]|L], Num1) :-
print_comps(L, Num1).
print_comps([], Num).
heading(N, 1) :-
!,
printf("\nCOMPONENT CONNECTIONS TO NODE %\n", [N]).
heading(N, X).
member(N1, [[N1, V, I]|Ls]).
member(N1, [[N2, V, I]|Ls]) :-
member(N1, Ls).
write_units(resistor, X) :-
printf("% Ohms",[X]).
write_units(capacitor, X) :-
printf("% Farads",[X]).
write_units(inductor, X) :-
printf("% Henrys", [X]).
write_units(current_source, X) :-
printf("% Ampere", [X]).
write_units(voltage_source, X) :-
printf("% Volts", [X]).
write_units(diode, X) :-
printf("type %", [X]).
write_units(transistor, X) :-
printf("type % (base, emitter, collector)", [X]).
write_units(transformer, X) :-
printf("ratio of %", [X]).
all_print([[Comp, Num, X|Nodes]|L]) :-
printf("% %: ", [Comp, Num]),
write_units(Comp, X),
printf("\n", []),
pr_nodes(Nodes),
all_print(L).
all_print([]).
pr_nodes([[N1, V1, I1]|X]) :-
printf(" Node %\n", [N1]),
printf(" Voltage %\n", [V1]),
printf(" Current %\n", [I1]),
pr_nodes(X).
pr_nodes([]) :-
printf("\n", []).
go1:-
W = 10,
Vs = 10,
R = 10,
L = 0.9,
C = 0.007,
circuit_solve(W,
[
[voltage_source,v1,c(Vs,0),[n1,n7]],
[resistor,r1,R,[n1,n2]],
[resistor,r2,R,[n1,n3]],
[resistor,r3,R,[n1,n4]],
[resistor,r4,R,[n1,n5]],
[resistor,r5,R,[n1,n6]],
[inductor,l1,L,[n2,n7]],
[inductor,l2,L,[n3,n7]],
[inductor,l3,L,[n4,n7]],
[inductor,l4,L,[n5,n7]],
[inductor,l5,L,[n6,n7]],
[capacitor,c1,C,[n2,n3]],
[capacitor,c2,C,[n2,n4]],
[capacitor,c3,C,[n2,n5]],
[capacitor,c4,C,[n2,n6]],
[capacitor,c5,C,[n3,n4]],
[capacitor,c6,C,[n3,n5]],
[capacitor,c7,C,[n3,n6]],
[capacitor,c8,C,[n4,n5]],
[capacitor,c9,C,[n4,n6]],
[capacitor,c10,C,[n5,n6]]
],
[n7],
[r1, r3, l1, l3, c8, l5]
).
% Output:
% resistor r1: 10 Ohms
% Node n1
% Voltage c(10, 0)
% Current c(0.552486, -0.497238)
% Node n2
% Voltage c(4.475138, 4.972376)
% Current c(-0.552486, 0.497238)
%
% resistor r3: 10 Ohms
% Node n1
% Voltage c(10, 0)
% Current c(0.552486, -0.497238)
% Node n4
% Voltage c(4.475138, 4.972376)
% Current c(-0.552486, 0.497238)
%
% inductor l1: 0.9 Henrys
% Node n2
% Voltage c(4.475138, 4.972376)
% Current c(0.552486, -0.497238)
% Node n7
% Voltage c(0, 0)
% Current c(-0.552486, 0.497238)
%
% inductor l3: 0.9 Henrys
% Node n4
% Voltage c(4.475138, 4.972376)
% Current c(0.552486, -0.497238)
% Node n7
% Voltage c(0, 0)
% Current c(-0.552486, 0.497238)
%
% capacitor c8: 0.007 Farads
% Node n4
% Voltage c(4.475138, 4.972376)
% Current c(0, 0)
% Node n5
% Voltage c(4.475138, 4.972376)
% Current c(0, 0)
%
% inductor l5: 0.9 Henrys
% Node n6
% Voltage c(4.475138, 4.972376)
% Current c(0.552486, -0.497238)
% Node n7
% Voltage c(0, 0)
% Current c(-0.552486, 0.497238)
%
go2:-
Vs = 10,
Tr1 = 5,
Tr2 = 0.2,
R1 = 1000,
R2 = 200,
R3 = 50,
R4 = 30,
circuit_solve(W,
[
[voltage_source, v1, c(Vs,0),[in, ground1]],
[resistor, r1, R2, [in, n1]],
[transformer, t1, Tr1,[n1, ground1, n2, ground2]],
[resistor, r2, R1, [n2, base]],
[transistor, q1, bc108, [base, n3, n4]],
[resistor, r3, R2, [n3, ground2]],
[resistor, r3, R2, [n4, ground2]],
[transformer, t2, Tr2,[n4, ground2, out, ground3]],
[resistor, r5, R4, [out, ground3]]
],
[ground1, ground2, ground3],
[n4, out]).
% Output:
% COMPONENT CONNECTIONS TO NODE n4
% transistor q1: type bc108 (base, emitter, collector)
% Node base
% Voltage c(1.909222, 0)
% Current c(9.005764e-005, 0)
% Node n3
% Voltage c(1.819164, 0)
% Current c(-0.009096, 0)
% Node n4
% Voltage c(-0.010742, 0)
% Current c(0.009006, 0)
%
% resistor r3: 200 Ohms
% Node n4
% Voltage c(-0.010742, 0)
% Current c(-5.371231e-005, 0)
% Node ground2
% Voltage c(0, 0)
% Current c(5.371231e-005, 0)
%
% transformer t2: ratio of 0.2
% Node n4
% Voltage c(-0.010742, 0)
% Current c(-0.008952, 0)
% Node ground2
% Voltage c(0, 0)
% Current c(0.008952, 0)
% Node out
% Voltage c(-0.053712, 0)
% Current c(0.00179, 0)
% Node ground3
% Voltage c(0, 0)
% Current c(-0.00179, 0)
%
%
% COMPONENT CONNECTIONS TO NODE out
% transformer t2: ratio of 0.2
% Node n4
% Voltage c(-0.010742, 0)
% Current c(-0.008952, 0)
% Node ground2
% Voltage c(0, 0)
% Current c(0.008952, 0)
% Node out
% Voltage c(-0.053712, 0)
% Current c(0.00179, 0)
% Node ground3
% Voltage c(0, 0)
% Current c(-0.00179, 0)
%
% resistor r5: 30 Ohms
% Node out
% Voltage c(-0.053712, 0)
% Current c(-0.00179, 0)
% Node ground3
% Voltage c(0, 0)
% Current c(0.00179, 0)
%
?- printf("\n>>> Sample goals: go1/0, go2/0\n", []).