https://school.programmers.co.kr/learn/courses/30/lessons/120866
나의 직독직해 구현 그 자체인 코드
def solution(board):
answer = 0
fix = []
board_lim = len(board)
# 수정할 이중배열 만들기
for i in range(len(board)):
fix.append([])
fix[i] += [0 for j in range(board_lim)]
# 돌면서 지뢰인 부분 찾아서 주변 위험지역으로 수정해주는 함수 소환
for n in range(board_lim):
for m in range(board_lim):
if board[n][m] == 1:
fix = dangerarea(n, m, board_lim, fix)
# 보드 전체 개수에서 수정된 위험지역 배열의 위험지역 개수 모두 더한걸 빼서 안전 지대 구하기
return board_lim * board_lim - sum([x for y in fix for x in y])
def dangerarea(n, m, board_lim, fix):
# n, m으로 지뢰 인덱스 받아와서 위험지역 다 1인 fix 이중배열 반환
fix[n][m] = 1
# 지뢰 행 수정 좌우로 끝보다 큰지 여부에 따라 좌우 수정
if m - 1 >= 0:
fix[n][m - 1] = 1
if m + 1 < board_lim:
fix[n][m + 1] = 1
# 세로 판단. 지뢰 위 행 수정
if n - 1 >= 0:
fix[n - 1][m] = 1
if m - 1 >= 0:
fix[n - 1][m - 1] = 1
if m + 1 < board_lim:
fix[n - 1][m + 1] = 1
# 세로 판단. 지뢰의 아래 행 수정
if n + 1 < board_lim:
fix[n + 1][m] = 1
if m - 1 >= 0:
fix[n + 1][m - 1] = 1
if m + 1 < board_lim:
fix[n + 1][m + 1] = 1
return fix
스터디원의 깔끔한 코드
스터디원이 근접~ 이런 문제 나오면 dx dy 로 푼다고 하셨다.
크... zip()도 덕분에 처음 알게 되었다.
def solution(board):
n = len(board)
pos = set([])
dx = [-1, -1, -1, 0, 0, 0, 1, 1, 1]
dy = [1, 0, -1, 1, -1, 0, 1, 0, -1]
for i, row in enumerate(board):
for j, col in enumerate(row):
if col == 1:
for x, y in zip(dx, dy):
if 0 <= i + x < n and 0 <= j + y < n:
pos.add((i + x, j + y))
return n * n - len(pos)
스터디원은 set에 인덱스 구성을 추가할때 애초에 그 범위 안에 있는 인덱스 구성만 추가해준 반면
타풀이 코드
타풀이에서는 그냥 다 추가한 후에 그 값이 범위 안에 있는 인덱스만 나중에 세서 더해줬다는게 엄청... 멋지다.
def solution(board):
n = len(board)
danger = set()
for i, row in enumerate(board):
for j, x in enumerate(row):
if not x:
continue
danger.update((i+di, j+dj) for di in [-1,0,1] for dj in [-1, 0, 1])
return n*n - sum(0 <= i < n and 0 <= j < n for i, j in danger)
위에 있는 danger.update()
set.update(set)
두 set을 결합해 기존 set을 수정한다. 중복시 한번만 포함시킨다.
아니 comprehension이 list, dict, set 동일한 방식으로 가능한거 나만 이제 알았나..?!
set = {이 안에 comprehension 포현식}
dict = {key:val 이후에 표현식} 출력값 표시 형식이 key:val 형식으로 출력. 표현식은 for key, val in enumerate()/zip() 이런식으로
zip()
여러 개의 순회 가능한(iterable) 객체를 인자로 받고, 각 객체가 담고 있는 원소를 튜플의 형태로 차례로 접근할 수 있는 반복자(iterator)를 반환
nums = [1, 2, 3]
chars = ["A", "B", "C"]
print(zip(nums, chars))
# 결과
<zip object at 0x0000021F0D730340>
for pair in zip(nums, chars):
print(pair)
# 결과
(1, 'A')
(2, 'B')
(3, 'C')
for x, y in zip(nums, chars):
print(x, y)
# 결과
1 A
2 B
3 C
인자가 2개일 필요 없고 그 이상도 가능
nums1 = [1, 2, 3]
nums2 = [10, 11, 12]
Bchars = ["A", "B", "C"]
Schars = ["a", "b", "c"]
for pair in zip(nums1, Bchars, Schars, nums2):
print(pair)
# 결과
(1, 'A', 'a', 10)
(2, 'B', 'b', 11)
(3, 'C', 'c', 12)
해체 하고 싶을 때도 zip() 함수 사용
리스트명 앞에 unpacking 연산자(*) 붙여서 다시 zip() 함수에 넘기면 다시 원래의 튜플을 얻을 수 있음
pairs = list(zip(nums, chars))
print(pairs)
# [(1, 'A'), (2, 'B'), (3, 'C')]
re_nums, re_chars = zip(*pairs)
print(re_nums)
# (1, 2, 3)
print(re_chars)
# ('A', 'B', 'C')
zip() 한걸로 dict(zip(인자, 인자)) 해서 두개의 리스트/ 튜플로 dictionary 만들 수 있음 (인자끼리 길이가 다르면 짧은것만 맞춰주고 버려짐)
'코테 공부 > python' 카테고리의 다른 글
[백준] #9372 Python 코테 스터디 -상근이의 여행 (그래프) (0) | 2023.06.09 |
---|---|
[프로그래머스] Python 평행 (0) | 2023.06.08 |
Python 외계어 사전, 요소 제거하면서 for문을 돌리면.. (0) | 2023.06.07 |
Python and or not 연산자 (0) | 2023.06.06 |
Python 코테 스터디 .maketrans(기존, 변경, 제외) / .translate(번역 매핑 테이블) / [] (빈 거) #False (0) | 2023.06.06 |