/* centigrade-fahrenheit relation */ cf(C,F) :- F = 1.8*C + 32. /* max relation: max(Z,X,Y) -- "Z is max of X and Y" */ max(X,X,Y) :- X > Y. max(Y,X,Y) :- X <= Y. /* append relation: append(Zs,Xs,Ys) -- like Zs = Xs ++ Ys */ append(Ys,[],Ys). append([X|Zs],[X|Xs],Ys) :- append(Zs,Xs,Ys). length([],0). length([_|Xs],N) :- N>0, length(Xs,N-1). ones([]). ones([1|Xs]) :- ones(Xs). flip_ones([1|Xs]) :- flip_ones(Xs). flip_ones([]). member(X,[X|Xs]). member(X,[Y|Ys]) :- member(X,Ys). fact(1,0). fact(P*N,N) :- N > 0, fact(P,N-1). flatten([],emptytree). flatten(List,node(Data,Left,Right)) :- flatten(LeftList,Left), flatten(RightList,Right), append(List,LeftList,[Data|RightList]). resistor(lead(I1,V1),lead(I2,V2),Ohms) :- I1+I2=0, V2-V1=I1*Ohms. battery(lead(I1,V1),lead(I2,V2),Volts) :- V1 = V2+Volts, I1+I2=0. electrical_ground(lead(0,0)). ammeter(lead(I1,V),lead(I2,V),I1) :- I1+I2=0. voltmeter(lead(0,V1),lead(0,V2),Volts) :- V1-V2=Volts. connect(Leads) :- same_voltages(Leads), currents_sum(Leads,0). same_voltages([]). same_voltages([L]). same_voltages([lead(I1,V),lead(I2,V)|More]) :- same_voltages([lead(I2,V)|More]). currents_sum([],0). currents_sum([lead(I1,V1)|More],I1+Sum) :- currents_sum(More,Sum). one_resistor(Volts,Ohms,Amps) :- battery(B1,B2,Volts), resistor(R1,R2,Ohms), ammeter(A1,A2,Amps), electrical_ground(G), connect([B2,A1]), connect([A2,R1]), connect([R2,B1,G]). divider(Volts,Ohms1,Ohms2,Amps,VCenter) :- battery(B1,B2,Volts), resistor(R1,R2,Ohms1), resistor(S1,S2,Ohms2), ammeter(A1,A2,Amps), voltmeter(V1,V2,VCenter), electrical_ground(G), connect([B2,A1]), connect([A2,R1]), connect([R2,S1,V1]), connect([S2,V2,B1,G]).