행렬의 곱셈 | 프로그래머스

김태영·2024년 6월 20일
0

코딩 테스트

목록 보기
22/33
post-thumbnail

📍 행렬의 곱셈

💡 문제

2차원 행렬 arr1과 arr2를 입력받아, arr1에 arr2를 곱한 결과를 반환하는 함수, solution을 완성해주세요.

⚠️ 제한사항

  • 행렬 arr1, arr2의 행과 열의 길이는 2 이상 100 이하입니다.
  • 행렬 arr1, arr2의 원소는 -10 이상 20 이하인 자연수입니다.
  • 곱할 수 있는 배열만 주어집니다.

✨ 행렬의 곱셈

단순히 arr1[i][j]arr2[i][j]를 곱하면 되는 줄 알았는데 아니었다. 행렬을 곱하는 방법이 따로 있다고 한다.

A 행렬(파란색)과 B 행렬(초록색)의 곱셈을 그림으로 설명하면 이런데.. 말로 설명하자면, A 행렬의 (0, 0)과 B 행렬의 (0, 0)을 곱한 값을 a라고 하고, A 행렬의 (0, 1)과 B 행렬의 (1, 0)을 곱합 값을 b라고 했을 때, A와 B의 행렬을 곱한 배열의 (0, 0)의 값은 a와 b를 더한 값과 같다.

즉, 결과는 A 행렬의 행 개수 * B 행렬의 열 개수 만큼의 크기를 지니게 된다.

✅ 풀이

👆 첫 번째 풀이 (성공)

공식 그대로 풀었다. arr1은 행은 고정된 채로 열의 값만 늘어나고, arr2는 열은 고정된 채로 행의 값만 늘어난다. 각각의 요소들을 곱한 값들을 fold를 사용해 더해주었다.

class Solution {
    fun solution(arr1: Array<IntArray>, arr2: Array<IntArray>): Array<IntArray> {
        // i는 행, j는 열
        return arr1.indices.map { i ->
            arr2[0].indices.map { j ->
            	// arr1의 행은 고정된다.
                // 순회하게 되면 별도의 인덱스 지정 없이 행은 고정된 채로 열의 값만 바뀐 요소들이 v에 들어온다.
                // idx는 열의 번호!
                arr1[i].foldIndexed(0) { idx, total, v ->
                    total + v * arr2[idx][j]
                }
            }.toIntArray()
        }.toTypedArray()
    }
}

🔥 다른 사람의 풀이

나는 각 행을 나타내는 배열을 IntArray로 바꿔주고, 전체 배열을 또 Array로 바꿔주었는데, 아예 배열 초기화를 사용해 형변환 없이 푼 사람이 있었다.

class Solution {
    fun solution(arr1: Array<IntArray>, arr2: Array<IntArray>): Array<IntArray> {
        var answer = Array<IntArray>(arr1.size) { i -> 
                Array<Int>(arr2[0].size) { j ->
                        var value = 0
                        for(n in 0 until arr1[i].size) {
                            value += (arr1[i][n] * arr2[n][j])
                        }
                        value
                }.toIntArray()
        }

        return answer
    }
}

💭 후기

행렬의 곱셈 방식을 알아보는 데 시간이 좀 걸렸다. 수학 공부 좀 열심히 할 걸 그랬다. 오늘 알게되었으니까 다음에 또 나오면 잘 풀 수 있겠지?

profile
화이팅

0개의 댓글

관련 채용 정보