Resistance calculator: Difference between revisions

Content added Content deleted
(Updated to compile with version 1.4. Removed tabulations, added parentheses. Removed useless imports, other minor modifications.)
Line 455: Line 455:


=={{header|Nim}}==
=={{header|Nim}}==
<lang python>import tables,strutils,sequtils,sugar,strformat
<lang python>import strutils, strformat


type
type
Node = ref object
Node = ref object
kind : char # + = serial * = parallel r = resistor
kind: char # + = serial * = parallel r = resistor
resistance : float
resistance: float
voltage : float
voltage: float
a : Node
a: Node
b : Node
b: Node


proc res(node : Node) : float =
proc res(node: Node): float =
if node.kind == '+' : return node.a.res + node.b.res
if node.kind == '+': return node.a.res + node.b.res
if node.kind == '*' : return 1/(1/node.a.res + 1/node.b.res)
if node.kind == '*': return 1 / (1 / node.a.res + 1 / node.b.res)
node.resistance
node.resistance


proc current(node : Node) : float = return node.voltage / node.res
proc current(node: Node): float = node.voltage / node.res
proc effect (node : Node) : float = return node.current * node.voltage
proc effect (node: Node): float = node.current * node.voltage


proc report(node : Node, level : string = "") =
proc report(node: Node, level: string = "") =
echo fmt"{node.res:8.3f} {node.voltage:8.3f} {node.current:8.3f} {node.effect:8.3f} {level}{node.kind}"
echo fmt"{node.res:8.3f} {node.voltage:8.3f} {node.current:8.3f} {node.effect:8.3f} {level}{node.kind}"
if node.kind in "+*":
if node.kind in "+*":
node.a.report level & "| "
node.a.report level & "| "
node.b.report level & "| "
node.b.report level & "| "


proc setVoltage(node : Node, voltage : float) =
proc setVoltage(node: Node, voltage: float) =
node.voltage = voltage
node.voltage = voltage
if node.kind == '+':
if node.kind == '+':
let ra = node.a.res
let ra = node.a.res
let rb = node.b.res
let rb = node.b.res
node.a.setVoltage ra/(ra+rb) * voltage
node.a.setVoltage ra / (ra+rb) * voltage
node.b.setVoltage rb/(ra+rb) * voltage
node.b.setVoltage rb / (ra+rb) * voltage
if node.kind == '*':
if node.kind == '*':
node.a.setVoltage voltage
node.a.setVoltage voltage
node.b.setVoltage voltage
node.b.setVoltage voltage


proc build(tokens : seq[string]) : Node =
proc build(tokens: seq[string]): Node =
var stack : seq[Node]
var stack: seq[Node]
for token in tokens:
for token in tokens:
if token == "+": stack.add Node(kind : '+', a : stack.pop, b : stack.pop)
stack.add if token == "+": Node(kind: '+', a: stack.pop, b: stack.pop)
elif token == "*": stack.add Node(kind : '*', a : stack.pop, b : stack.pop)
elif token == "*": Node(kind: '*', a: stack.pop, b: stack.pop)
else: stack.add Node(kind : 'r', resistance : parseFloat(token))
else: Node(kind: 'r', resistance: parseFloat(token))
stack.pop
stack.pop


proc calculate(voltage:float, tokens:seq[string]): Node =
proc calculate(voltage: float, tokens: seq[string]): Node =
echo ""
echo ""
echo " Ohm Volt Ampere Watt Network tree"
echo " Ohm Volt Ampere Watt Network tree"
let node = build tokens
let node = build tokens
node.setVoltage voltage
node.setVoltage voltage
node.report
node.report
node</lang>
node</lang>


===RPN===
===RPN===
<lang python>proc rpn(voltage:float, s:string): Node = calculate(voltage, s.split ' ')
<lang python>proc rpn(voltage:float, s:string): Node = calculate(voltage, s.split ' ')
var node = rpn 18.0,"10 2 + 6 * 8 + 6 * 4 + 8 * 4 + 8 * 6 +"
var node = rpn(18, "10 2 + 6 * 8 + 6 * 4 + 8 * 4 + 8 * 6 +")
assert 10 == node.res
assert 10 == node.res
assert 18 == node.voltage
assert 18 == node.voltage
Line 517: Line 517:
===Infix===
===Infix===
<lang python>proc parse(s: string): seq[string] =
<lang python>proc parse(s: string): seq[string] =
var tmp = ""
var tmp = ""
for ch in s:
for ch in s:
if ch == ' ':
case ch
of ' ':
if tmp!="": result.add tmp
tmp = ""
if tmp != "": result.add tmp
tmp = ""
continue
continue
if ch in "+*()":
of '+', '*', '(', ')':
if tmp!="": result.add tmp
if tmp != "": result.add tmp
tmp=""
tmp = ""
result.add fmt"{ch}"
result.add $ch
else: tmp &= ch
else:
if tmp!="": result.add tmp
tmp &= ch
if tmp != "": result.add tmp


proc shuntRPN(s:string): seq[string] =
proc shuntRPN(s: string): seq[string] =
let ops = "+*"
let ops = "+*"
var tokens = parse s
var tokens = parse s
var stack: seq[string]
var stack: seq[string]
var op: string
var op: string

for token in tokens:
for token in tokens:
case token
case token
of "(": stack.add token
of "(":
stack.add token
of ")":
of ")":
while stack.len > 0:
op = stack.pop()
while stack.len > 0:
if op == "(": break
op = stack.pop()
if op == "(": break
result.add op
result.add op
else:
else:
if token in ops:
if token in ops:
while stack.len > 0:
while stack.len > 0:
op = stack[^1]
op = stack[^1]
if not (op in ops): break
if ops.find(token) >= ops.find(op): break
if op notin ops: break
if ops.find(token) >= ops.find(op): break
discard stack.pop()
discard stack.pop()
result.add op
result.add op
stack.add token
else: result.add token
stack.add token
else: result.add token

while stack.len > 0: result.add stack.pop()
while stack.len > 0: result.add stack.pop()


proc infix(voltage:float, s:string): Node = calculate(voltage, shuntRPN s)
proc infix(voltage:float, s:string): Node = calculate(voltage, shuntRPN s)
node = infix 18.0,"((((10+2)*6+8)*6+4)*8+4)*8+6"
node = infix(18, "((((10+2)*6+8)*6+4)*8+4)*8+6")
assert 10 == node.res
assert 10 == node.res
assert 18 == node.voltage
assert 18 == node.voltage