在重温《编码:隐匿在计算机软硬件背后的语言》第12章——二进制加法器时,心血来潮用JS写了一个模拟串行加法器。
测试断言工具TestUtils.js
function assertTrue(actual){
if(!actual)
throw "Error actual: " + actual + " is not true."
}
function assertFalse(actual){
if(actual)
throw "Error actual: " + actual + " is not false."
}
function assertIntEquals(expected, actual){
if(typeof expected != "number")
throw "Error expected: " + expected +" is not a number."
if(typeof actual != "number")
throw "Error actual: " + actual +" is not a number."
if(expected != actual)
throw "Error expected: " + expected + " and actual: " + actual +" is different."
}
十进制数与二进制数之间转换工具utils.js
function int2LowEightBitArray(num){
var result = []
for(var i = 0; i < 8; i++)
result.push(((num >> i) & 1) == 1)
return result
}
function lowEightBitArray2Int(array){
var result = 0
for(var i = 0; i < 8; i++){
if(array[i])
result += (1 << i)
}
return result
}
function lowNineBitArray2Int(array){
var result = 0
for(var i = 0; i < 9; i++){
if(array[i])
result += (1 << i)
}
return result
}
//用补码表示负数
function int2EightBitArray(num){
if(num < -128 || num > 127){
throw "Out of boundary(-128, 127)."
}
var result = []
for(var i = 0; i < 8; i++)
result.push(((num >> i) & 1) == 1)
return result
}
function eightBitArray2Int(array){
var result = 0
for(var i = 0; i < 7; i++){
if(array[i])
result += (1 << i)
}
if(array[i])
result += -128
return result
}
function int2SixteenBitArray(num){
if(num < -(1 << 15) || num > (1 << 15) - 1){
throw "Out of boundary({left}, {right})."
.replace("{left}", -(1 << 15))
.replace("{right}", (1 << 15) - 1)
}
var result = []
for(var i = 0; i < 16; i++)
result.push(((num >> i) & 1) == 1)
return result
}
function sixteentBitArray2Int(array){
var result = 0
for(var i = 0; i < 15; i++){
if(array[i])
result += (1 << i)
}
if(array[i])
result += -(1 << 15)
return result
}
加法器模型model.js
class DoubleInGate{
#id
#in1
#in2
#gateTypeName
#func
#out
#lastOut
#outReceiver
#outReceiverInName
constructor(id, gateTypeName, in1 = false, in2 = false, func){
this.#id = id
this.#gateTypeName = gateTypeName
this.#in1 = in1
this.#in2 = in2
this.#func = func
this.#out = this.#func(this.in1, this.in2)
// this.#lastOut = this.#out
}
updateIn1(flag){
this.#in1 = flag
this.#updateOut()
}
updateIn2(flag){
this.#in2 = flag
this.#updateOut()
}
getOut(){
return this.#out;
}
updateBothIn(in1 = false, in2 = false){
this.#in1 = in1
this.#in2 = in2
this.#updateOut()
}
setOutReceiver(outReceiver, inName){
this.#outReceiver = outReceiver
this.#outReceiverInName = inName
}
#updateOut(){
this.#lastOut = this.#out
this.#out = this.#func(this.#in1, this.#in2)
if(this.#out != this.#lastOut){
this.#send(this.#out)
}
}
#send(flag){
if(this.#outReceiver){
this.#outReceiver.receive(this.#outReceiverInName, flag)
}
}
receive(inName, flag){
if(inName == "in1"){
this.updateIn1(flag)
}else if(inName == "in2"){
this.updateIn2(flag)
}
}
toString(){
return "{gateTypeName} id: {id}, in1: {in1}, in2: {in2}, out:{out}"
.replace("{gateTypeName}", this.#gateTypeName)
.replace("{id}", this.#id)
.replace("{in1}", this.#in1)
.replace("{in2}", this.#in2)
.replace("{out}", this.#out)
}
}
//与门
class AndGate extends DoubleInGate
最低0.47元/天 解锁文章
1027

被折叠的 条评论
为什么被折叠?



