Created
March 4, 2017 12:17
-
-
Save GlulkAlex/3e0c6adf3531121d39317a65d83d1e9b to your computer and use it in GitHub Desktop.
Exercise from Discrete Event Simulation Lecture of Functional Program Design In Scala course
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/env scala | |
// for The `bash` `shell script` './script.sh' | |
// but App main object warper must be disabled|excluded | |
import scala.io.AnsiColor._ | |
// it is imported twice in the same scope by | |
//import scala.Console._ | |
// | |
// | |
/*object digital_Circuit_Logic_Gates extends App */{ | |
/* A digital circuit is composed | |
of wires | |
and of functional components. | |
*/ | |
// conducting only {true|false} signals | |
class Wire { | |
// error: abstract member may not have private modifier | |
private var signal: Boolean = true | |
// | |
def get_Signal: Boolean = signal | |
// | |
def set_Signal(s_Val: Boolean): Unit = { | |
//this. | |
signal = s_Val} | |
} | |
// | |
/* | |
The components have | |
a reaction time (or delay), | |
i.e. their outputs don't change immediately | |
after a change to their inputs. | |
*/ | |
/** output is the inverse of its input */ | |
def inverter(input: Wire, output: Wire): Unit = { | |
//output = !input | |
output.set_Signal(!input.get_Signal) | |
} | |
// | |
/** output is the conjunction of its inputs */ | |
def and_Gate( | |
a1: Wire, | |
a2: Wire, | |
output: Wire | |
): Unit = { | |
//output = a1 && a2 | |
output.set_Signal(a1.get_Signal && a2.get_Signal) | |
} | |
// | |
/** output is the disjunction of its inputs */ | |
def or_Gate( | |
o1: Wire, | |
o2: Wire, | |
output: Wire | |
): Unit = { | |
//output = o1 || o2 | |
output.set_Signal(o1.get_Signal || o2.get_Signal) | |
} | |
// | |
def half_Adder( | |
a: Wire, b: Wire, s: Wire, c: Wire | |
): Unit = { | |
val d = new Wire | |
val e = new Wire | |
// | |
or_Gate(a, b, d) | |
and_Gate(a, b, c) | |
inverter(c, e) | |
and_Gate(d, e, s) | |
} | |
// | |
def full_Adder( | |
a: Wire, b: Wire, cin: Wire, sum: Wire, cout: Wire | |
): Unit = { | |
val s = new Wire | |
val c1 = new Wire | |
val c2 = new Wire | |
// | |
half_Adder(b, cin, s, c1) | |
half_Adder(a, s, sum, c2) | |
or_Gate(c1, c2, cout) | |
} | |
// | |
def unknown_Gate( | |
a: Wire, | |
b: Wire, | |
c: Wire | |
): Unit = { | |
val d, e, f, g = new Wire | |
// | |
inverter(a, d) | |
inverter(b, e) | |
and_Gate(a, e, f) | |
and_Gate(b, d, g) | |
or_Gate(f, g, c) | |
} | |
// | |
def mark_String( | |
str: String, | |
expected_Val: Any, | |
actual_Val: Any | |
): String = if ( | |
expected_Val == actual_Val | |
){ | |
REVERSED + str + RESET | |
} else { | |
str | |
} | |
// | |
def log_2(x: Int): Int = (math.log(x) / math.log(2)).toInt | |
// scala> 3.toBinaryString | |
// res1: String = 11 | |
//java.lang.Integer.parseInt(String s, int radix) | |
val combination_Size = 2 | |
// pairs|combinations_Size|length | |
val range_Upper_Limit: Int = math.pow(2, combination_Size).toInt | |
val str_Max_Binary_Size = log_2(range_Upper_Limit)// + 1 | |
val choices: Map[Char, Boolean] = Map('0' -> false, '1' -> true) | |
var results_Comparisons: Map[String, List[Boolean]] = Map( | |
"a_And_Not_B" -> List(), | |
"a_Equal_B" -> List(), | |
"a_And_Not_A_And_B" -> List(), | |
"a_Not_Equal_B" -> List(), | |
"Not_A_And_B" -> List() | |
) | |
val test_Wire = new Wire | |
// | |
println("(test_Wire = new Wire).get_Signal:" + test_Wire.get_Signal) | |
test_Wire.set_Signal(false) | |
println("(test_Wire.set_Signal(false).get_Signal:" + test_Wire.get_Signal) | |
println("Combinations of {0|1} of length:" + combination_Size) | |
println("000111".combinations(3).toList.mkString("\n")) | |
println(List(0, 1, 0).permutations.toArray.mkString("\n")) | |
(0 until range_Upper_Limit by 1).foreach(i => { | |
// | |
val b_Str = i.toBinaryString | |
val size_Diff = str_Max_Binary_Size - b_Str.size | |
val a = new Wire | |
val b = new Wire | |
val c = new Wire | |
// | |
if (size_Diff > 0) { | |
// | |
a.set_Signal(false) | |
b.set_Signal(choices(b_Str(0))) | |
// | |
println("0" * size_Diff + b_Str) | |
} else { | |
a.set_Signal(choices(b_Str(0))) | |
b.set_Signal(choices(b_Str(1))) | |
// | |
println(b_Str) | |
} | |
// | |
println("unknown_Gate(a:" + a.get_Signal + | |
", b:" + b.get_Signal + | |
", c:" + c.get_Signal + ")") | |
unknown_Gate( | |
a, | |
b, | |
c | |
) | |
val actual_Result = c.get_Signal | |
val a_And_Not_B = a.get_Signal && !b.get_Signal | |
val a_Equal_B = a.get_Signal == b.get_Signal | |
val a_And_Not_A_And_B = a.get_Signal && !(a.get_Signal && b.get_Signal) | |
val a_Not_Equal_B = a.get_Signal != b.get_Signal | |
val Not_A_And_B = !a.get_Signal && b.get_Signal | |
// | |
results_Comparisons += "a_And_Not_B" -> ( | |
(actual_Result == a_And_Not_B) :: results_Comparisons.getOrElse("a_And_Not_B", List[Boolean]()) | |
) | |
results_Comparisons += "a_Equal_B" -> ( | |
(actual_Result == a_Equal_B) :: results_Comparisons.getOrElse("a_Equal_B", Nil) | |
) | |
results_Comparisons += "a_And_Not_A_And_B" -> ( | |
(actual_Result == a_And_Not_A_And_B) :: results_Comparisons.getOrElse( | |
"a_And_Not_A_And_B", Nil) | |
) | |
results_Comparisons += "a_Not_Equal_B" -> ( | |
(actual_Result == a_Not_Equal_B) :: results_Comparisons.getOrElse("a_Not_Equal_B", Nil) | |
) | |
results_Comparisons += "Not_A_And_B" -> ( | |
(actual_Result == Not_A_And_B) :: results_Comparisons.getOrElse("Not_A_And_B", Nil) | |
) | |
// | |
println( | |
"c:" + c.get_Signal + | |
mark_String( | |
"\n?= (a && !b):" + a_And_Not_B, a_And_Not_B, actual_Result) + | |
//"\n?= (a && !b):" + a_And_Not_B + | |
mark_String( | |
"\n?= (a == b):" + a_Equal_B, a_Equal_B, actual_Result) + | |
//"\n?= (a == b):" + (a.get_Signal == b.get_Signal) + | |
mark_String( | |
"\n?= (a && !(a && b)):" + a_And_Not_A_And_B, | |
a_And_Not_A_And_B, actual_Result) + | |
//"\n?= (a && !(a && b)):" + (a.get_Signal && !(a.get_Signal && b.get_Signal)) + | |
mark_String( | |
"\n?= (a != b):" + a_Not_Equal_B, a_Not_Equal_B, actual_Result) + | |
//"\n?= (a != b):" + (a.get_Signal != b.get_Signal) + | |
mark_String( | |
"\n?= (!a && b):" + Not_A_And_B, Not_A_And_B, actual_Result) + | |
//"\n?= (!a && b):" + (!a.get_Signal && b.get_Signal) + | |
//" ?= (a * b):" + a.get_Signal == b.get_Signal + | |
"\n" | |
) | |
} | |
) | |
// | |
Console.println("digital_Circuit_Logic_Gates: ...") | |
println( | |
results_Comparisons | |
.filter{case (k, v) => v.forall(i => i)} | |
) | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment