[백준] 10830번: 행렬 제곱 - Kotlin[코틀린]

2024. 3. 6. 21:11·알고리즘/Baekjoon

문제

 

 

10830번: 행렬 제곱

크기가 N*N인 행렬 A가 주어진다. 이때, A의 B제곱을 구하는 프로그램을 작성하시오. 수가 매우 커질 수 있으니, A^B의 각 원소를 1,000으로 나눈 나머지를 출력한다.

www.acmicpc.net

 


풀이

 

 곱셈 공식을 활용한 분할 정복을 수행하는 재귀 함수로 해결하면 된다. (1629번 곱셈 문제와 같다.) 재귀 함수에서는 다음과 같이 지수를 반으로 나눠가며 계산한다. 지수가 1인 경우에 입력받은 행렬을 그대로 리턴하면 된다.

 

  - 지수가 짝수인 경우
    $a^n = a^{n/2} \times a^{n/2}$


  - 지수가 홀수인 경우
    $a^n = a^{n/2} \times a^{n/2}\times a$

 

 행렬의 곱셈은 다음 이미지와 같은 방식으로 처리되며, 3중 for문으로 구현할 수 있다. 매우 큰 수의 방지를 위해 1000L으로 모듈러 연산을 해준다.

이미지 출처 - 위키 백과

 


코드

 

fun main() {
    val br = System.`in`.bufferedReader()
    val bw = System.out.bufferedWriter()

    val line = br.readLine().split(' ')
    val size = line[0].toInt()
    val num = line[1].toLong()
    val matrix = Array(size) { br.readLine().split(' ').map { it.toLong() % 1000L }.toLongArray() }

    val sb = StringBuilder()
    for (row in power(matrix, num)) {
        sb.append("${row.joinToString(" ") { it.toString() }}\n")
    }

    bw.write(sb.toString())
    bw.flush()
    bw.close()
    br.close()
}

fun multi(mat1: Array<LongArray>, mat2: Array<LongArray>): Array<LongArray> {
    val size = mat1.size
    val tmp = Array(size) { LongArray(size) }

    for (i in 0 until size) {
        for (j in 0 until size) {
            for (k in 0 until size) {
                tmp[i][j] += mat1[i][k] * mat2[k][j]
                tmp[i][j] %= 1000L
            }
        }
    }

    return tmp
}

fun power(mat: Array<LongArray>, exponent: Long): Array<LongArray> {
    return when(exponent) {
        1L -> mat
        else -> {
            val n = power(mat, exponent / 2)

            if (exponent % 2 == 0L) multi(n, n)
            else multi(multi(n, n), mat)
        }
    }
}

 

'알고리즘 > Baekjoon' 카테고리의 다른 글

[백준] 11444번: 피보나치 수 6 - Kotlin[코틀린]  (0) 2024.03.10
[백준] 2961번: 도영이가 만든 맛있는 음식 - Kotlin[코틀린]  (1) 2024.03.07
[백준] 1747번: 소수&팰린드롬 - Kotlin[코틀린]  (0) 2024.03.05
[백준] 1629번: 곱셈 - Kotlin[코틀린]  (0) 2024.03.04
[백준] 16194번: 카드 구매하기 2 - Kotlin[코틀린]  (0) 2024.03.03
'알고리즘/Baekjoon' 카테고리의 다른 글
  • [백준] 11444번: 피보나치 수 6 - Kotlin[코틀린]
  • [백준] 2961번: 도영이가 만든 맛있는 음식 - Kotlin[코틀린]
  • [백준] 1747번: 소수&팰린드롬 - Kotlin[코틀린]
  • [백준] 1629번: 곱셈 - Kotlin[코틀린]
junghoooooon
junghoooooon
  • junghoooooon
    코드팁스
    junghoooooon
  • 전체
    오늘
    어제
    • 전체 (120)
      • 안드로이드 (0)
        • 코드팁스 (0)
      • 유니티 (0)
        • 코드팁스 (0)
      • 알고리즘 (118)
        • 알고리즘 (0)
        • Baekjoon (118)
      • GitHub (0)
      • 티스토리 (2)
  • 블로그 메뉴

    • 링크

    • 공지사항

    • 인기 글

    • 태그

      MST
      크루스칼
      그래프 탐색
      피보나치
      DP
      재귀
      모듈러 곱셈 역원
      투 포인터
      브루트포스
      스택
      에라토스테네스의 체
      유니온파인드
      BFS
      수학
      그리디
      dfs
      분리집합
      구현
      그래프이론
      정렬
      문자열
      분할 정복
      우선순위 큐
      큐
      누적 합
      이분 탐색
      프림
      티스토리
      백트래킹
      소수 판정
    • hELLO· Designed By정상우.v4.10.2
    junghoooooon
    [백준] 10830번: 행렬 제곱 - Kotlin[코틀린]
    상단으로

    티스토리툴바