요구능력: DFS와 BFS 그리고 스택과 큐의 이해
코드설명 :
1. 1번 배열을 상,하 반전
이건 arr이 2차원 배열이기 때문에 reverse()하면 arr[i][j]일 때, arr[i]의 순서가 거꾸로 되므로 상하반전이 된다.
2. 2번 배열을 좌, 우 반전
좌, 우 반전은 arr[i][j]에서 j(열)을 반전시켜주면 된다.
3. 배열을 오른쪽으로 90도 회전
이 부분에서 조금 헤맸다.
n과 m을 스왑안해줘서 원하는 결과가 계속 안나왔다.
n과 m을 스왑해줄거면 resultArr도 새로 생성해줘야한다.
어차피 밑에서 arr에 다 넣어주기 때문에 저장은 되어있다.
그리고 배열문제를 잘 푸려면 인덱스 활용을 잘해야된다.
resultArr이 0,0일 때 arr은 5,0을 내주어야 한다.
이런식으로 쭉 나열해서 적어보면 코드에서 아래식이 나온 이유를 알게될 것이다.
4. 배열을 왼쪽으로 90도 회전
3번과 마찬가지이다.
5. 1번그룹 -> 2번그룹, 2번그룹 -> 3번그룹, 3번그룹 -> 4번그룹, 4번그룹 -> 1번그룹
이게 이 문제의 핵심이 아닐까 싶다.
( 6* 8 을 기준으로 설명)
이것도 마찬가지로 배열을 하나하나 다 적어보고 인덱스 식을 찾으면 된다.
1번 영역의 인덱스
arr[0][0...3]
arr[1][0...3]
arr[2][0...3]
2번 영역의 인덱스
arr[0][4...7]
arr[1][4...7]
arr[2][4...7]
3번 영역의 인덱스
arr[3][4...7]
arr[4][4...7]
arr[5][4...7]
4번 영역의 인덱스
arr[3][0...3]
arr[4][0...3]
arr[5][0...3]
한번에 구할 방법은 도저히 생각나지 않아서 구역을 나눠서 풀었다.
한개의 예시만 이해하면 다 해결할 수 있을것이다.
예시로 4번에서 1번가는걸 설명해보자면
우선 resultArr[i][j]에 맞춰서 for문의 범위를 구해보자
4번에서 1번가려면 resultArr은 1번 자리에서 기준을 잡아야된다.
1번자리는 0~3번까지밖에 가지 않는걸 볼 수 있다.
이건 for문을 n과 m의 절반씩만 돌리면 된다는 의미이다.
그럼 for문을 만들었으니 거기에 맞춰서 4번 자리를 구해주면 된다.
arr[(n / 2) + i][j] 이렇게 하면 4번자리의 인덱스들이 구해진다.
이해가 가지 않는다면 resultArr의 인덱스에 들어가야되는 arr의 인덱스를 적어서 나열해보면 이해가 갈것이다.
왼쪽이 resultArr 오른쪽이 arr이라면 아래와 같다.
0 0 | 3 0
0 1 | 3 1
0 2 | 3 2
0 3 | 3 3
.
.
.
이렇게 직접 써가면서 해보면 식을 찾기 쉬울 것이다.
6. 1번그룹 -> 4번그룹, 4번그룹 -> 3번그룹, 3번그룹 -> 2번그룹, 2번그룹 -> 1번그룹
5번과 같은 방식으로 찾으면 된다.
후기 : 배열관련문제는 많이 풀어볼수록 속도가 빨라질것같다.
이번문제를 통해 배열에 대한 이해도와 숙련도가 상승한것같다.
이해가 가지않는다면 댓글 달아주시면 도움을 드리겠습니다.
let read = readLine()!.split(separator: " ").map{Int(String($0))!}
var n = read[0]
var m = read[1]
let r = read[2]
var count = 0
var arr = Array(repeating: Array(repeating: 0, count: m), count: n)
var resultArr :[[Int]] = Array(repeating: Array(repeating: 0, count: m), count: n)
for i in 0..<n {
arr[i] = readLine()!.split(separator: " ").map{Int($0)!}
}
let a = readLine()!.split(separator: " ").map{String($0)}
for k in 0..<a.count{
if count < r {
switch a[k]{
case "1":
resultArr = arr.reversed()
arr = resultArr
count += 1
case "2":
for i in 0..<n{
resultArr[i] = arr[i].reversed()
}
arr = resultArr
count += 1
case "3":
swap(&n, &m)
resultArr = Array(repeating: Array(repeating: 0, count: m), count: n)
for i in 0..<n{
for j in 0..<m{
resultArr[i][j] = arr[m - 1 - j][i]
}
}
arr = resultArr
count += 1
case "4":
swap(&n, &m)
resultArr = Array(repeating: Array(repeating: 0, count: m), count: n)
for i in 0..<n{
for j in 0..<m{
resultArr[i][j] = arr[j][n - 1 - i]
}
}
arr = resultArr
count += 1
case "5":
// 4 -> 1
for i in 0..<n/2{
for j in 0..<m/2{
resultArr[i][j] = arr[(n / 2) + i][j]
}
}
// 1 -> 2
for i in 0..<n/2{
for j in m/2..<m{
resultArr[i][j] = arr[i][j - (m/2)]
}
}
// 2 -> 3
for i in n/2..<n{
for j in m/2..<m{
resultArr[i][j] = arr[i - n/2][j]
}
}
// 3 -> 4
for i in n/2..<n{
for j in 0..<m/2{
resultArr[i][j] = arr[i][j + m/2]
}
}
arr = resultArr
count += 1
case "6":
// 1 -> 4
for i in n/2..<n{
for j in 0..<m/2{
resultArr[i][j] = arr[i - (n / 2)][j]
}
}
// 2 -> 1
for i in 0..<n/2{
for j in 0..<m/2{
resultArr[i][j] = arr[i][j + (m/2)]
}
}
// 3 -> 2
for i in 0..<n/2{
for j in m/2..<m{
resultArr[i][j] = arr[i + n/2][j]
}
}
// 4 -> 3
for i in n/2..<n{
for j in m/2..<m{
resultArr[i][j] = arr[i][j - m/2]
}
}
arr = resultArr
count += 1
default:
break
}
}
}
for i in 0..<n {
print(arr[i].map{String($0)}.joined(separator: " "))
}
'Algorithm > 문제풀이_백준' 카테고리의 다른 글
[Swift][DP] 백준 11053번 (가장 긴 증가하는 부분수열) (0) | 2021.09.22 |
---|---|
[Swift][문자열] 백준 10973번 (이전순열) (0) | 2021.09.16 |
[Swift][DFS/BFS] 백준 1260번 (DFS와 BFS) (0) | 2021.09.09 |
[Swift][Stack] 백준 10828번 (스택) (0) | 2021.09.09 |
[Swift][BruteForce] 백준 3085번 (사탕게임) (0) | 2021.09.09 |
댓글