마방진은 정사각형 격자 안에 숫자를 배열하여 모든 행, 열, 대각선의 합이 동일하게 되도록 하는 숫자 배열입니다.
이러한 배열을 대충 파이썬 코드를 작성해서 찾아보면 뿐만 아니라 더 큰 수에서도 찾을 수 있으며
import numpy as np
from multiprocessing import Pool
# 홀수 차수의 마방진 생성
def generate_odd_magic_square(n):
magic_square = np.zeros((n,n), dtype=int)
num = 1
i, j = 0, n//2
while num <= n*n:
magic_square[i, j] = num
num += 1
newi, newj = (i-1) % n, (j+1) % n
if magic_square[newi, newj]:
i += 1
else:
i, j = newi, newj
return magic_square
# 4n차수의 마방진 생성
def generate_doubly_even_magic_square(n):
arr = [[(n*y)+x+1 for x in range(n)]for y in range(n)]
for i in range(0,n//4):
for j in range(0,n//4):
arr[i][j] = (n*n + 1) - arr[i][j];
for i in range(0,n//4):
for j in range(3 * (n//4),n):
arr[i][j] = (n*n + 1) - arr[i][j];
for i in range(3 * (n//4),n):
for j in range(0,n//4):
arr[i][j] = (n*n + 1) - arr[i][j];
for i in range(3 * (n//4),n):
for j in range(3 * (n//4),n):
arr[i][j] = (n*n + 1) - arr[i][j];
for i in range(n//4,3 * (n//4)):
for j in range(n//4,3 * (n//4)):
arr[i][j] = (n*n + 1) - arr[i][j];
return np.array(arr)
# 4n+2차수의 마방진 생성
def generate_singly_even_magic_square(s):
if s % 2 == 1:
s += 1
while s % 4 == 0:
s += 2
q = [[0 for j in range(s)] for i in range(s)]
z = s // 2
b = z * z
c = 2 * b
d = 3 * b
o = generate_odd_magic_square(z)
for j in range(0, z):
for i in range(0, z):
a = o[i][j]
q[i][j] = a
q[i + z][j + z] = a + b
q[i + z][j] = a + c
q[i][j + z] = a + d
lc = z // 2
rc = lc
for j in range(0, z):
for i in range(0, s):
if i < lc or i > s - rc or (i == lc and j == lc):
if not (i == 0 and j == lc):
t = q[i][j]
q[i][j] = q[i][j + z]
q[i][j + z] = t
return np.array(q)
def generate_magic_square(n):
if n % 2 == 1:
return generate_odd_magic_square(n)
elif n % 4 == 0:
return generate_doubly_even_magic_square(n)
else:
return generate_singly_even_magic_square(n)
def is_valid_magic_square(magic_square):
n = len(magic_square)
magic_sum = np.sum(magic_square, axis=0)[0]
return (
all(np.sum(magic_square, axis=0) == magic_sum) and
all(np.sum(magic_square, axis=1) == magic_sum) and
np.sum(np.diag(magic_square)) == magic_sum and
np.sum(np.diag(np.fliplr(magic_square))) == magic_sum
)
def worker(n):
magic_square = generate_magic_square(n)
result_str = f'Magic Square of order {n}x{n}:\n'
result_str += str(magic_square) + '\n'
result_str += f'Magic sum: {np.sum(magic_square, axis=0)[0]}\n'
result_str += f'Is valid magic square: {is_valid_magic_square(magic_square)}\n'
return result_str
if __name__ == "__main__":
orders = list(range(3, 11))
with Pool() as pool:
results = pool.map(worker, orders)
for result in results:
print(result)
그때 각 선들의 합은 다음 식을 만족합니다.
특이한 것은 마방진 중에서 다음 배열은
각 수를 제곱해도 마방진이 됩니다.
import numpy as np
def is_valid_magic_square(magic_square):
n = len(magic_square)
magic_sum = np.sum(magic_square, axis=0)[0]
# Check the sum of each row, column, and the two diagonals
return (
all(np.sum(magic_square, axis=0) == magic_sum) and
all(np.sum(magic_square, axis=1) == magic_sum) and
np.sum(np.diag(magic_square)) == magic_sum and
np.sum(np.diag(np.fliplr(magic_square))) == magic_sum
)
# Provided magic square
magic_square = np.array([
[256, 676, 1, 529, 1444, 2704, 1849, 3721],
[1681, 3969, 1600, 2500, 9, 441, 196, 784],
[1296, 2916, 2025, 3481, 100, 1024, 49, 289],
[25, 361, 144, 900, 2209, 3249, 1156, 3136],
[729, 169, 484, 16, 2401, 1521, 4096, 1764],
[3844, 1936, 2601, 1369, 576, 4, 625, 225],
[3025, 1089, 3364, 2304, 841, 121, 400, 36],
[324, 64, 961, 81, 3600, 2116, 2809, 1225]
])
print(is_valid_magic_square(magic_square))