프로그래밍/Python

[Python] 마방진 그리기 / 검산하기 with numpy

Lou Park 2021. 2. 12. 23:58

극한탈출 999의 문제

극한탈출 999

오늘 트위치에서 <극한탈출 999> 라는 방탈출게임 게임방송을 보다 저런 퍼즐을 발견했다. 1~9까지 핀이 주어지고 가로, 세로, 대각선의 합이 15가되도록 만드는건데 찾아보니 이것을 마방진이라고 부른다!

 

마방진...영어이름도 Magic Square...11차마법진을 그릴수있다면 정말 멋질거야....

 

내가 상상한 마방진

 

 

마방진 그리는 방법 

마방진을 그리는 방법은 아래 사진과 같다. 인터넷에 원리라고 떠돌아다니는 건데....원리는 잘 모르겠다 ㅋㅋㅋ 암튼 파이썬으로 마방진 생성기를 만들어 보자. 11차 마방진이든 111차 마방진이든 그릴수 있도록 말이다.

 

 

파이썬으로 마방진 그리기

numpy 라이브러리를 사용할 것 이므로 코드 최상단에 import numpy as np 를 까먹지말자. 난 까먹었지만.

def get_next(m, size, r, c):
    dr = r - 1
    dc = c + 1

    if dr < 0:
        dr = size - 1
    elif dc >= size:
        dc = 0

    try:
        # 자리가 꽉찬경우 or 배열 바운더리를 벗어난 경우
        if m[dr][dc] != 0:
            raise IndexError()
    except IndexError:
        dc = c
        dr = r + 1

    return dr, dc


if __name__ == '__main__':
    try:
        size = int(input("홀수 입력:"))

        if size % 2 == 1:
            # size x size 크기의 0으로 채워진 2차원 배열 생성
            m = np.zeros((size, size))

            # 첫번째줄 가운데에서 시작
            r = 0
            c = int(size / 2)

            # 1부터 차례로 채워나감
            for i in range(1, size * size + 1):
                if i != 1:
                    r, c = get_next(m, size, r, c)
                m[r][c] = f'{i:03}'

            print("===== 마방진 =====")
            print(m)
            print("================")
            npm = np.matrix(m)

            # 검산하기
            print(npm.sum(axis=0)) # column의 합
            print(npm.sum(axis=1)) # row의 합
            print(np.trace(np.asarray(m))) # \ 방향 대각선 합
            print(np.trace(np.fliplr(np.asarray(m)))) # / 방향 대각선
        else:
            print("홀수를 입력해야합니다.")

    except ValueError:
        print("정수를 입력해야 합니다.")

 

 

 

출력 결과

마방진을 보여주고 합을 구하여 제대로 마방진이 만들어졌는지 확인한다.

홀수 입력:9
===== 마방진 =====
[[47. 58. 69. 80.  1. 12. 23. 34. 45.]
 [57. 68. 79.  9. 11. 22. 33. 44. 46.]
 [67. 78.  8. 10. 21. 32. 43. 54. 56.]
 [77.  7. 18. 20. 31. 42. 53. 55. 66.]
 [ 6. 17. 19. 30. 41. 52. 63. 65. 76.]
 [16. 27. 29. 40. 51. 62. 64. 75.  5.]
 [26. 28. 39. 50. 61. 72. 74.  4. 15.]
 [36. 38. 49. 60. 71. 73.  3. 14. 25.]
 [37. 48. 59. 70. 81.  2. 13. 24. 35.]]
================
[[369. 369. 369. 369. 369. 369. 369. 369. 369.]]
[[369.]
 [369.]
 [369.]
 [369.]
 [369.]
 [369.]
 [369.]
 [369.]
 [369.]]
369.0
369.0

numpy가 뭔지 맛보다가 마방진으로 새어버렸다...하지만 이정도라면 numpy  맛보기는 한거같은데?!