prepare multiply.py for release and add script for automatic calculation testing
This commit is contained in:
parent
6cda8bcfa0
commit
1ab5b67c77
|
@ -0,0 +1,27 @@
|
||||||
|
import multiply as mlt
|
||||||
|
|
||||||
|
top_value = int("0b" + input("Top value (in binary): "), 2)
|
||||||
|
m = int(input("Method: "))
|
||||||
|
|
||||||
|
total_iterations = (top_value + 1) ** 2
|
||||||
|
print(f"Total test amount: {top_value + 1}^2 = {total_iterations}")
|
||||||
|
|
||||||
|
errors = []
|
||||||
|
|
||||||
|
for x in range(top_value):
|
||||||
|
for y in range(top_value):
|
||||||
|
n = max([len(bin(i)[2:]) for i in (x, y)])
|
||||||
|
expected_result = mlt.al(bin(x*y)[2:], 2*n)
|
||||||
|
|
||||||
|
_, r = mlt.multiply(n, x, y, m)
|
||||||
|
|
||||||
|
if r == expected_result:
|
||||||
|
print(f"{str(x*top_value+y).rjust(len(str(total_iterations)))}/{total_iterations}", end = "\r")
|
||||||
|
else:
|
||||||
|
errors.append([x, y, expected_result, r])
|
||||||
|
print(f"Failed at {x}*{y}; expected {expected_result} but got {r}!")
|
||||||
|
|
||||||
|
if len(errors) == 0:
|
||||||
|
print("Testing finished, no miscalculations detected.\nIt's safe to use!")
|
||||||
|
else:
|
||||||
|
print("Testing failed with {len(errors)} errors.")
|
|
@ -8,52 +8,90 @@ def align_binary_to_right(value, size):
|
||||||
|
|
||||||
al = align_binary_to_right
|
al = align_binary_to_right
|
||||||
|
|
||||||
def multiply(x, y, method):
|
def multiply(n, x, y, method):
|
||||||
|
'''
|
||||||
|
this method can be used to:
|
||||||
|
- get step-by-step binary multiplication data using different methods;
|
||||||
|
- get just the end result of binary multiplication;
|
||||||
|
|
||||||
|
it takes 4 arguments:
|
||||||
|
n - (int) base register bit depth
|
||||||
|
x - (int) value for X operand
|
||||||
|
y - (int) value for Y operand
|
||||||
|
method - (int) which method to use to perform multiplication
|
||||||
|
|
||||||
|
it returns 2 items:
|
||||||
|
- (list) table with step-by-step operations and descriptions
|
||||||
|
- (str) binary representation of the result
|
||||||
|
|
||||||
|
Methods fully supported: №4
|
||||||
|
'''
|
||||||
|
|
||||||
if method == 4:
|
if method == 4:
|
||||||
n = len(bin(x)[2:]) # base registry bit length, usually written as n
|
|
||||||
|
|
||||||
# every table line has registers like so: RG1, RG3, RG2
|
# every table line has registers like so: RG1, RG3, RG2
|
||||||
data_table = [[["0"*(2*n+1), "0" + bin(y)[2:] + "0"*n, bin(x)[2:], "-"]]*2]
|
data_table = [[["0", "0"*(2*n+1), "0" + al(bin(y)[2:], n) + "0"*n, al(bin(x)[2:], n), "-"]]*2]
|
||||||
|
|
||||||
while int('0b' + data_table[-1][-1][2], 2) != 0:
|
# iteration number
|
||||||
|
i = 0
|
||||||
|
|
||||||
|
while int('0b' + data_table[-1][-1][3], 2) != 0:
|
||||||
data_table.append([])
|
data_table.append([])
|
||||||
|
i += 1
|
||||||
|
|
||||||
if data_table[-2][-1][2][0] == "1":
|
if data_table[-2][-1][3][0] == "1":
|
||||||
data_table[-1].append([
|
data_table[-1].append([
|
||||||
al(bin(int("0b"+data_table[-2][-1][0], 2) + int("0b"+data_table[-2][-1][1], 2))[-(2*n+1):], 2*n+1), # RG1 + RG3
|
i,
|
||||||
data_table[-2][-1][1],
|
al(bin(int("0b"+data_table[-2][-1][1], 2) + int("0b"+data_table[-2][-1][2], 2))[-(2*n+1):], 2*n+1), # RG1 + RG3
|
||||||
data_table[-2][-1][2],
|
data_table[-2][-1][2],
|
||||||
|
data_table[-2][-1][3],
|
||||||
"RG1+RG3"
|
"RG1+RG3"
|
||||||
])
|
])
|
||||||
|
|
||||||
data_table[-1].append([
|
data_table[-1].append([
|
||||||
data_table[-1][-1][0],
|
i,
|
||||||
'0' + data_table[-1][-1][1][:-1], # 0.r(RG3)
|
data_table[-1][-1][1],
|
||||||
data_table[-1][-1][2][1:] + '0', # l(RG2).0
|
'0' + data_table[-1][-1][2][:-1], # 0.r(RG3)
|
||||||
|
data_table[-1][-1][3][1:] + '0', # l(RG2).0
|
||||||
"0.r(RG3), l(RG2).0"
|
"0.r(RG3), l(RG2).0"
|
||||||
])
|
])
|
||||||
|
|
||||||
else:
|
else:
|
||||||
data_table[-1].append([
|
data_table[-1].append([
|
||||||
data_table[-2][-1][0],
|
i,
|
||||||
'0' + data_table[-2][-1][1][:-1], # 0.r(RG3)
|
data_table[-2][-1][1],
|
||||||
data_table[-2][-1][2][1:] + '0', # l(RG2).0
|
'0' + data_table[-2][-1][2][:-1], # 0.r(RG3)
|
||||||
|
data_table[-2][-1][3][1:] + '0', # l(RG2).0
|
||||||
"0.r(RG3), l(RG2).0"
|
"0.r(RG3), l(RG2).0"
|
||||||
])
|
])
|
||||||
|
|
||||||
return data_table
|
return data_table, data_table[-1][-1][1][:-1]
|
||||||
|
|
||||||
|
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
x = int("0b" + input("X: "), 2)
|
# a fully functional reference
|
||||||
y = int("0b" + input("Y: "), 2)
|
# implementation for this library
|
||||||
|
# is provided below
|
||||||
|
|
||||||
|
raw_x = input("X: ")
|
||||||
|
raw_y = input("Y: ")
|
||||||
|
|
||||||
|
if len(raw_x) == len(raw_y):
|
||||||
|
n = len(raw_x)
|
||||||
|
else:
|
||||||
|
n = int(input("n: "))
|
||||||
|
|
||||||
|
x = int("0b" + raw_x, 2)
|
||||||
|
y = int("0b" + raw_y, 2)
|
||||||
|
|
||||||
method = int(input("Method: "))
|
method = int(input("Method: "))
|
||||||
dt = multiply(x, y, method)
|
|
||||||
|
dt, result = multiply(n, x, y, method)
|
||||||
|
|
||||||
from lib.prettytable import PrettyTable
|
from lib.prettytable import PrettyTable
|
||||||
pt = PrettyTable()
|
pt = PrettyTable()
|
||||||
pt.field_names = ["RG1", "RG3", "RG2", "Operations"]
|
pt.field_names = ["Iteration", "RG1", "RG3", "RG2", "Operations"]
|
||||||
|
|
||||||
for i in dt[1:]:
|
for i in dt:
|
||||||
for j in range(len(i)):
|
for j in range(len(i)):
|
||||||
if j+1 == len(i):
|
if j+1 == len(i):
|
||||||
pt.add_row(i[j], divider = True)
|
pt.add_row(i[j], divider = True)
|
||||||
|
@ -61,3 +99,4 @@ if __name__ == "__main__":
|
||||||
pt.add_row(i[j])
|
pt.add_row(i[j])
|
||||||
|
|
||||||
print(pt)
|
print(pt)
|
||||||
|
print(f"Result: {result}")
|
||||||
|
|
Loading…
Reference in New Issue