https://www.acmicpc.net/problem/19236
19236번: 청소년 상어
첫째 줄부터 4개의 줄에 각 칸의 들어있는 물고기의 정보가 1번 행부터 순서대로 주어진다. 물고기의 정보는 두 정수 ai, bi로 이루어져 있고, ai는 물고기의 번호, bi는 방향을 의미한다. 방향 bi는
www.acmicpc.net
Problem
- 오늘은 청소년 상어가 이 공간에 들어가 물고기를 먹으려고 한다. 청소년 상어는 (0, 0)에 있는 물고기를 먹고, (0, 0)에 들어가게 된다. 상어의 방향은 (0, 0)에 있던 물고기의 방향과 같다. 이후 물고기가 이동한다.
- 4×4크기의 공간이 있고, 크기가 1×1인 정사각형 칸으로 나누어져 있다.
- 공간의 각 칸은 (x, y)와 같이 표현하며, x는 행의 번호, y는 열의 번호이다. 한 칸에는 물고기가 한 마리 존재한다.
- 각 물고기는 번호와 방향을 가지고 있다. 번호는 1보다 크거나 같고, 16보다 작거나 같은 자연수이며, 두 물고기가 같은 번호를 갖는 경우는 없다. 방향은 8가지 방향(상하좌우, 대각선) 중 하나이다.
- 상어가 먹을 수 있는 물고기 번호의 합의 최댓값을 구해보자.
조건
- 물고기는 번호가 작은 물고기부터 순서대로 이동한다. 물고기는 한 칸을 이동할 수 있고, 이동할 수 있는 칸은 빈 칸과 다른 물고기가 있는 칸, 이동할 수 없는 칸은 상어가 있거나, 공간의 경계를 넘는 칸이다. 각 물고기는 방향이 이동할 수 있는 칸을 향할 때까지 방향을 45도 반시계 회전시킨다. 만약, 이동할 수 있는 칸이 없으면 이동을 하지 않는다. 그 외의 경우에는 그 칸으로 이동을 한다. 물고기가 다른 물고기가 있는 칸으로 이동할 때는 서로의 위치를 바꾸는 방식으로 이동한다.
- 물고기의 이동이 모두 끝나면 상어가 이동한다. 상어는 방향에 있는 칸으로 이동할 수 있는데, 한 번에 여러 개의 칸을 이동할 수 있다. 상어가 물고기가 있는 칸으로 이동했다면, 그 칸에 있는 물고기를 먹고, 그 물고기의 방향을 가지게 된다. 이동하는 중에 지나가는 칸에 있는 물고기는 먹지 않는다. 물고기가 없는 칸으로는 이동할 수 없다. 상어가 이동할 수 있는 칸이 없으면 공간에서 벗어나 집으로 간다. 상어가 이동한 후에는 다시 물고기가 이동하며, 이후 이 과정이 계속해서 반복된다.
SOL
초등학생 상어, 어른 상어 문제를 푸니까 , 이번에는 청소년 상어가 나왔다.
상어들이 왜이렇게 많을까 , 우리나라는 사실 상어 강국?
구현하는데는 큰 무리가 없었지만, 중간에 물고기가 움직이는 부분을 따로 함수로 처리해줬었는데,
거기서, 물고기가 죽은 정보가 제대로 반영이 되지않는 오류가 발생했었다.
결국 원인은 찾지못한채로, 일단 DFS 구문안에 그때마다 찾아서 물고기를 움직여주는걸로 바꿔주었다. :(
# 청소년 상어 ~
# 상어가 움직이는 부분
# 물고기가 이동하는 부분
# 물고기는 번호 순서대로 이동한다.
# 물고기는 이동할 곳이 없으면, 방향을 돈다. (반시계방향 45도)
# 상어는 먹은 물고기의 방향으로 움직인다.(방향에 있는 어떤 물고기든 다 먹을수 있음.)
import sys
import copy
sys.setrecursionlimit(10**6)
input= sys.stdin.readline
board=[[0 for _ in range(4)] for _ in range(4)]
fishLst=[x for x in range(17)]
dx=[0,-1,-1,-1,0,1,1,1]
dy=[-1,-1,0,1,1,1,0,-1]
tmp = [list(map(int,input().split())) for _ in range(4)]
for i in range(4):
for j in range(4):
board[i][j] = [tmp[i][j*2],tmp[i][j*2+1]-1]
#print(board)
#init
ans=0
def dfs(sy,sx,score,board):
global ans
score +=board[sy][sx][0]
ans=max(ans,score)
board[sy][sx][0] =0
#물고기가 움직여요. 물고기 정보도 반영해줍니다.
for f in range(1,17):
#물고기가 잡아 먹혔는지, 안잡아먹혔는지 check
loc =None
for y in range(4):
for x in range(4):
if board[y][x][0] ==f:
loc =(y,x)
if not loc:
continue
# 물고기가 살아 있다면, 방향을 돌려준다.
y,x =loc
fdir =board[y][x][1]
for k in range(8):
nd =(fdir+k)%8
ny = y+dy[nd]
nx = x+dx[nd]
if not (0<=ny<4 and 0<=nx<4) or (ny==sy and nx==sx):
continue
board[y][x][1] = nd
board[y][x],board[ny][nx] = board[ny][nx],board[y][x]
break
#fish_moving(sy,sx)
# 상어가 움직인다
s_d=board[sy][sx][1]
for k in range(1,5):
ny=sy+dy[s_d]*k
nx=sx+dx[s_d]*k
if (0<=ny<4 and 0<=nx<4) and board[ny][nx][0]>0:
dfs(ny,nx,score,copy.deepcopy(board))
dfs(0,0,0,board)
print(ans)
'알고리즘 문제(SOL)' 카테고리의 다른 글
[백준/1181/파이썬] 단어 정렬 (0) | 2022.03.01 |
---|---|
[백준/1012/파이썬] 유기농 배추 (0) | 2022.03.01 |
[백준/12865/파이썬] 평범한 배낭 (0) | 2022.02.28 |
[백준/7579/파이썬] 앱 (0) | 2022.02.28 |
[백준/24542/파이썬] 튜터-튜티 관계의 수 (0) | 2022.02.27 |