Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
40 changes: 40 additions & 0 deletions Hongjoo/lv2/N개의최소공배수.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
"""
링크 : https://school.programmers.co.kr/learn/courses/30/lessons/12953

n개의 숫자들의 최소 공배수
Inspect :n 개의 숫자들이 모두 "1" 이 될 때 까지 2~100의 자연수들의 값으로 나누기
ex)
[2,6,8,14]
e = 2 : [1,3,4,7] => elements = [2]
e = 3 : [1.1.4.7] => elements = [2,3]
e = 4 : [1,1,1,7] => elements = [2,3,4]
e = 5 : [1,1,1,7] => 유지
e = 6 ...

"""
def solution(arr) :
answer = 1
elements = []

e = 2
# 1.
while e<=100 or arr.count(1) != len(arr) :

flag = False
#2. 해당 e 로 배열 arr 가 나누어 떨어지는 지 확인 -> 떨어지면 flag = True , 해당 arr[k] 은 e의 몫으로 구성함
for k in range(len(arr)) :
if arr[k] == 1 :
continue
if arr[k] % e == 0 :
arr[k] =arr[k] // e
flag = True
#3. 해당 e 값이 배열 arr 의 값 중 하나 이상의 구성 요소일때 , 최소공배수 구성워소 elements 배열에 추가
if flag :
elements.append(e)
else : # 해당 값이 구성 원소 아닐 경우 -> 다음 e 로 다시 도전하기
e+= 1


for e in elements :
answer*= e
return answer
39 changes: 9 additions & 30 deletions Hongjoo/lv2/가장큰수.py
Original file line number Diff line number Diff line change
@@ -1,35 +1,14 @@
"""
실패
1. 가장 큰 자리수 비교 -> 자리수 가장 작은 수
0. graph
idx : numbers
value : [0,0,0,-1] # ex 62 => [6,2,False,False]
# 조건 2.
3,30,300 비교 -> 3 > 30> 300 우선순위
#반례
1) 110 vs 1 > 1+110
2) [12, 1213] -> 1213+12
https://www.programmers.co.kr/learn/courses/30/lessons/42746
"""

def solution(numbers):
answer = ''
#0. graph 만들기
graph = list()
for n in numbers:
p = 4-len(str(n))
if p > 0 :
douple_n = str(n)*p
else :
douple_n = str(n)
graph.append([douple_n[:4], p ]) # 자리수 맞춰주기(4자리)
# print(graph)
#2.정렬 : 높은 자리수의 값이 큰 순서 대로
graph.sort(key=lambda x : x[0] , reverse = True)
# print(graph)
#3. 합치기
answer=""
for i in range(len(graph)):
num = graph[i][0] ; position = 4-graph[i][1]
answer += str(int(num[:position]))# "000","0" 경우 0으로 처리

# 1. number의 같은 길이에 대해서 크기 비교하기
numbers_str = [str(num) for num in numbers ] # 문자열로 변환
numbers = sorted(numbers_str ,key = lambda x: x*3 , reverse = True )
#2. 리스트 원소를 1개의 문자열로 출력 형식 충족하기
# answer = "".join(numbers)
# print(answer , type(answer))
answer = str(int("".join(numbers)))
# print(answer , type(answer))
return answer
54 changes: 54 additions & 0 deletions Hongjoo/lv2/거리두기확인하기.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
"""
[프로그래머스] 거리두기 확인하기: 백트레킹 / lv2
https://school.programmers.co.kr/learn/courses/30/lessons/81302
"""
from collections import deque

dy =[1,-1,0,0] ; dx=[0,0,-1,1]
def solution(places):
answer = []
for place in places :
# 1. 응시자 위치 확인
people = []
for i in range(5) :
for j in range(5) :
if place[i][j] == "P":
people.append([i,j])
#2. 응시자 별로 거리 확인하기
def bfs(start):
clv = 0
visited = [[-1]*5 for _ in range(5)] # 거리 저장하기(lv)
q = deque([start])
visited[start[0]][start[1]] = 0
while q :
cy,cx = q.popleft()
clv = visited[cy][cx]
if clv >= 2 :
break
for d in range(4):
ny,nx = cy + dy[d] , cx +dx[d]
if 0<= ny < 5 and 0 <= nx < 5 and visited[ny][nx] <= -1 :
if place[ny][nx] == "X":
visited[ny][nx] = clv +1
continue
elif place[ny][nx] == "O":
q.append([ny,nx])
visited[ny][nx] = clv +1
elif place[ny][nx] == "P" :
return False
return True
flag = True
for p in range(len(people)):
start = people[p]
flag = bfs(start)
if not flag :
break
if flag:
answer.append(1)
else :
answer.append(0)


# print(people)
# print(f"answer{answer}")
return answer
26 changes: 26 additions & 0 deletions Hongjoo/lv2/전화번호목록.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
"""
https://school.programmers.co.kr/learn/courses/30/lessons/42577
"""

def solution(phone_book):
answer = True
#1. 글자수로 정렬하기
phone_book = sorted(phone_book , key = lambda x : (len(x)))
#2. key = 전번인 해쉬맵 생성
hash_map = {}
for phone in phone_book :
hash_map[phone] = 1
#3. hashmap에 접두어 비교하기
for phone in phone_book :
tmp = ""
# 접두어 한 글자씩 추가해서 hasp_map의 key들 중에 같은게 있는지 확인
for n in phone :
tmp += n
if tmp in hash_map and tmp!= phone :
answer = False





return answer
52 changes: 52 additions & 0 deletions Hongjoo/백준/계란으로계란치기.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
"""
[BOJ]#16987.계란으로계란치기:백트레킹/골드5
https://www.acmicpc.net/problem/16987
"""
import sys

#0. 입력 변수 정의 및 초기화 하기
input= sys.stdin.readline
N = int(input())
eggs = [[] for _ in range(N)]

for i in range(N):
durability , weight =map(int ,input().split())
eggs[i] = [durability , weight]

# 1. backtracking 수행하기
max_cnt = 0
def backtracking(idx,cnt) :
global max_cnt
print(f"stage {idx}")
# pruning 조건 : 현재 남은 횟수로 2개씩 깨도 max_cnt 업데이트 불가 경우
if max_cnt >= (cnt + (N-idx)*2):
return 0
#1. 종료 조건 : (1. 모든 계란 선택 완료 n == N)
if idx >= N : # 1개 이하 남아있을떄
max_cnt = max(max_cnt , cnt)
return 0

#1-2. 현재 선택한 계란 (idx) 가 깨져있는 경우
if eggs[idx][0] <= 0 :
backtracking(idx+1 , cnt)
#2.동작 과정- 계란 깨기
else : # 현재 계란 lived -> 부딫힐 계란 선택 & 부딫치기
flag =False
for j in range(N) :#현재 계란 부딫칠 계란 선택 (본인idx 아님 or 생존 )
if j!= idx and eggs[j][0] > 0 :
# 충돌
eggs[idx] =eggs[idx] -eggs[j][1]
eggs[j] =eggs[j] -eggs[idx][1]
backtracking(idx+1 , cnt+int(eggs[idx][0]<=0) + int(eggs[j][0]<=0) ) # 충돌 계산하기
flag = True
# 충돌 원상 복귀
eggs[idx] =eggs[idx] +eggs[j][1]
eggs[j] =eggs[j] +eggs[idx][1]
# 한 번도 안 깨짐 -> 선택한 idx 내려두고 다음 idx +1 로 이동
if not flag :
backtracking(idx+1 , cnt )

return 0

backtracking(0 ,0)
print(max_cnt)
40 changes: 40 additions & 0 deletions Hongjoo/백준/로또.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
"""
[BOJ]6603로또/실버2
https://www.acmicpc.net/problem/6603

-주어진 K개(k>6) 숫자에 6개 뽑아 대해 중복x 한 조합의 경우의 수 찾기
->중복 x , 순서 상관x
- 해당 모든 경우의 수는 사전 순으로 출력
- 입력 : K , {해당하는 숫자의 조합}
"""

import sys
input = sys.stdin.readline
# 1. 입력 변수 및 출력 형식에 맞춰 설정하기
while True :
set_s = list(map(int, input().split()))
answer = []
if len(set_s) < 2 :
break
k= set_s.pop(0)
#2. 유효성 검사 is_valid 정의
# check = [True]*len(set_s[1:])
result = [0]*6 # 출력 리스트
#3. 백트래킹 함수 정의
def conbination(level ,idx ):
#종료 조건
if level == 6 :
answer.append(result.copy())
# print(result)
return
# 동작 과정
for i in range(idx,k):
result[level] = set_s[i]
conbination(level+1 ,i+1) # 조합은 idx 보다 작은 i는 탐색 할 필요 없음
result[level] = 0
conbination(0,0)
# print(answer)
# 3. 출력 형식 맞추기
for a in answer:
print(" ".join(map(str,a)))
print("")
39 changes: 39 additions & 0 deletions Hongjoo/백준/문자열거리.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
"""
## [백준] #1230. 문자열거리: DP / 골드1
> 문제 링크 : https://www.acmicpc.net/problem/1230
"""
import sys
input = sys.stdin.readline
# 0. 입력 변수 정의 및 초기화 하기
o = list(input())
l = list(input())
INF = 1000
if len(l) < len(o) :
print(-1)
exit()
#1. dp 정의
# dp[i][j][0] : de[i][j]로 O[:i] == L[:j]
dp = [[[0,0] for j in range(len(l)+1)] for i in range(len(o)+1)]
# 초기화
dp[0][0] = [0,INF]
for j in range(1,len(l)+1):
dp[0][j][1] = 1
dp[0][j][0] = INF
# for i in range(len(o)+1):
# dp[i][0][0] = -1

# #2. 점화식
for i in range(len(o)) :
for j in range(i+1):
dp[i+1][j][0] = dp[i+1][j][1] = INF
for j in range(i, len(l)):
if o[i] == l[j] :
dp[i+1][j+1][0] = min(dp[i][j][0] , dp[i][j][1])
else :
dp[i+1][j+1][0] = INF
dp[i+1][j+1][1] = min(dp[i+1][j][0] +1 , dp[i+1][j][1])
#3. 출력
if min(dp[-1][-1][0],dp[-1][-1][1]) >= INF :
print(-1)
else :
print(min(dp[-1][-1][0] , dp[-1][-1][1]))
81 changes: 81 additions & 0 deletions Hongjoo/백준/안전영역.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,81 @@
""""
실버1
https://www.acmicpc.net/problem/2468
# 조건 :
(1) 물에 잠기지 않은 구역 위치 구하기
(2) 안 잠긴 구역들의 군집 개수 찾기
- 상하좌우로 연결된 구역 = 1 군집
# 유형: 노드 탐색 -> BFS/DFS
연결된 노드들이 이루는 군집 개수 구하는 문제


"""
import sys
from collections import deque
input = sys.stdin.readline

n = int(input())
field = []
limit_list= set()
limit_list.add(0)
# 1. 물에 잠김, 생존 구역으로 구분한 field 만들기
for i in range(n):
tmp = list(map(int,input().split()))
for j in range(n) :
# limit_list 수집하기 = 노드의 높이 값 종류
limit_list.add(tmp[j])
field.append(tmp)
# print(f"field - {limit_list}")


# 종류별 limit에 따라 지대 높이가 limit 이하일 경우 침수되는 지역, 생존 지역 명시
# board : 생존 여부 + 방문 여부 확인 flag 역할
def init_board(limit) :
# 각 limit 별로 침수되는 지역을 확인하기
board = [[0 for _ in range(n)] for k in range(n) ]
saved_point = []
# 침수 지역 맵 업데이트하기
for i in range(n):
for k in range(n):
if field[i][k] <= limit : # 침수 지역
board[i][k] =-1
else :
# 생존 지역
saved_point.append([i,k])
return board,saved_point

# 2. 생존 구역들의 군집 개수 구하기
#상하좌우
dy =[-1,1,0,0 ]
dx = [0,0,-1,1]
def bfs(sy,sx , field):
# (1)시작점 정의
q = deque()
q.append([sy,sx])
field[sy][sx] = 1 # 방문 등록
# (2)인접한 노드
while q :
cy,cx =q.popleft()
for dw in range(4):
ny,nx = cy + dy[dw] , cx +dx[dw]
# 2-1 필드 범위에서 벗어나는지 확인
# 2-2방문 여부 확인
if 0<= ny < n and 0<= nx < n and field[ny][nx] == 0 : # 방문 안했으면 업데이트
q.append([ny,nx])
field[ny][nx] = 1

return 0
# main 함수
max_cnt = 0
for limit in limit_list : #limit 을 1개씩 조합해봄
board,saved_point = init_board(limit)
# print(f"##{limit} : {saved_point}")
cnt = 0
# 생존 구역에서 확인
for y,x in saved_point :
if board[y][x] == 0 :#방문 안했으면 -> bfs 탐색 진행
bfs(y,x, board)
cnt +=1

max_cnt = max(max_cnt , cnt)
print(max_cnt)
Loading