728x90

https://programmers.co.kr/learn/courses/30/lessons/68935

출처 : 프로그래머스

 

코딩테스트 연습 - 3진법 뒤집기

자연수 n이 매개변수로 주어집니다. n을 3진법 상에서 앞뒤로 뒤집은 후, 이를 다시 10진법으로 표현한 수를 return 하도록 solution 함수를 완성해주세요. 제한사항 n은 1 이상 100,000,000 이하인 자연수

programmers.co.kr


def solution(n):
    answer = 0
    tmp = []
    
    while True:
        tmp.append(n % 3)
        n //= 3
        if n == 0:
            break       
            
    idx = 0  
    for t in tmp[::-1]:
        if t == 0:
            idx += 1
            continue
        answer += t*(3**idx)
        idx += 1
        
    return answer

풀이

3으로 나눈 나머지로 3진법을 구하는 방법으로 구했다.

하지만 다른 사람 풀이를 보고 놀랐다..ㅋ ㅋ ...

def solution(n):
    tmp = ''
    
    while True:
        tmp += str(n % 3)
        n //= 3
        if n == 0:
            break
            
    answer = int(tmp,3)
    return answer

풀이

int('문자열', 진법)

솔직히 int가 이런 옵션이 있는줄 몰랐다.

앞으로 진법문제 나올 때 유용하게 쓰자.

728x90

https://programmers.co.kr/learn/courses/30/lessons/77884

출처 : 프로그래머스

 

코딩테스트 연습 - 약수의 개수와 덧셈

두 정수 left와 right가 매개변수로 주어집니다. left부터 right까지의 모든 수들 중에서, 약수의 개수가 짝수인 수는 더하고, 약수의 개수가 홀수인 수는 뺀 수를 return 하도록 solution 함수를 완성해주

programmers.co.kr


def solution(left, right):
    answer = 0
    for i in range(left,right+1):
        cnt = 0 # 약수 개수 카운트
        for j in range(1,i+1):
            if i % j == 0: # 약수면
                cnt += 1
        if cnt % 2 == 0: # 약수 개수가 짝수면 더하고
            answer += i
        else: # 약수 개수가 홀수면 빼기
            answer -= i
    return answer

풀이

left부터 right까지 하나씩 약수의 개수를 구한다.

약수의 개수가 짝수면 answer 에 더해주고

약수의 개수가 홀수면 answer 에서 빼준다.

728x90

문제

그룹 단어란 단어에 존재하는 모든 문자에 대해서, 각 문자가 연속해서 나타나는 경우만을 말한다. 예를 들면, ccazzzzbb는 c, a, z, b가 모두 연속해서 나타나고, kin도 k, i, n이 연속해서 나타나기 때문에 그룹 단어이지만, aabbbccb는 b가 떨어져서 나타나기 때문에 그룹 단어가 아니다.

단어 N개를 입력으로 받아 그룹 단어의 개수를 출력하는 프로그램을 작성하시오.

입력

첫째 줄에 단어의 개수 N이 들어온다. N은 100보다 작거나 같은 자연수이다. 둘째 줄부터 N개의 줄에 단어가 들어온다. 단어는 알파벳 소문자로만 되어있고 중복되지 않으며, 길이는 최대 100이다.

출력

첫째 줄에 그룹 단어의 개수를 출력한다.

코드

import sys
n = int(sys.stdin.readline())
cnt = 0
for i in range(n):
    s = sys.stdin.readline().rstrip()
    new_word = [s[0]]
    err = 0
    for a in range(len(s)-1):
        if s[a] != s[a+1]:
            if s[a+1] in new_word:
                err += 1
            new_word.append(s[a+1])

    if err == 0:
        cnt += 1
print(cnt)

풀이

입력받은 문자열을 한 글자씩 비교하면서 다른 글자가 나오면 new_word에 넣는다.

이때, new_word에 있는 글자라면 그룹 단어가 되지 않으니 체크한다.

 

출처 : 백준

728x90

문제

1부터 N까지의 수로 이루어진 순열이 있다. 이때, 사전순으로 다음에 오는 순열을 구하는 프로그램을 작성하시오.

사전 순으로 가장 앞서는 순열은 오름차순으로 이루어진 순열이고, 가장 마지막에 오는 순열은 내림차순으로 이루어진 순열이다.

N = 3인 경우에 사전순으로 순열을 나열하면 다음과 같다.

  • 1, 2, 3
  • 1, 3, 2
  • 2, 1, 3
  • 2, 3, 1
  • 3, 1, 2
  • 3, 2, 1

입력

첫째 줄에 N(1 ≤ N ≤ 10,000)이 주어진다. 둘째 줄에 순열이 주어진다.

출력

첫째 줄에 입력으로 주어진 순열의 다음에 오는 순열을 출력한다. 만약, 사전순으로 마지막에 오는 순열인 경우에는 -1을 출력한다.

코드

# 10972
import sys
n = int(sys.stdin.readline())
arr = list(map(int,sys.stdin.readline().split()))
x = 0
for i in range(n-1, 0, -1):
    if arr[i] > arr[i-1]:
        x = i-1
        break
for i in range(n-1, 0, -1):
    if arr[x] < arr[i]:
        arr[x], arr[i] = arr[i], arr[x]
        arr = arr[:x+1] + sorted(arr[x+1:])
        print(*arr)
        exit()
print(-1)

풀이

 next_permutation

  1. 순열의 뒤 부터 비교하며 뒷 값이 앞 값 보다 큰 인덱스 구해서 x에 앞 값 인덱스 넣기
  2. 이 x 값과 다시 순열의 뒤부터 비교해서 arr[x] 보다 큰 값 구하고 swap 진행하기
  3. x 다음 값이 큰 값이었다.
  4. 이 값 기준으로 앞은 그대로, 뒤는 sorted 해서 포인트로 접근 print()
  5. exit() 종료
728x90

문제

준규가 사는 나라는 우리가 사용하는 연도와 다른 방식을 이용한다. 준규가 사는 나라에서는 수 3개를 이용해서 연도를 나타낸다. 각각의 수는 지구, 태양, 그리고 달을 나타낸다.

지구를 나타내는 수를 E, 태양을 나타내는 수를 S, 달을 나타내는 수를 M이라고 했을 때, 이 세 수는 서로 다른 범위를 가진다. (1 ≤ E ≤ 15, 1 ≤ S ≤ 28, 1 ≤ M ≤ 19)

우리가 알고있는 1년은 준규가 살고있는 나라에서는 1 1 1로 나타낼 수 있다. 1년이 지날 때마다, 세 수는 모두 1씩 증가한다. 만약, 어떤 수가 범위를 넘어가는 경우에는 1이 된다.

예를 들어, 15년은 15 15 15로 나타낼 수 있다. 하지만, 1년이 지나서 16년이 되면 16 16 16이 아니라 1 16 16이 된다. 이유는 1 ≤ E ≤ 15 라서 범위를 넘어가기 때문이다.

E, S, M이 주어졌고, 1년이 준규가 사는 나라에서 1 1 1일때, 준규가 사는 나라에서 E S M이 우리가 알고 있는 연도로 몇 년인지 구하는 프로그램을 작성하시오.

입력

첫째 줄에 세 수 E, S, M이 주어진다. 문제에 나와있는 범위를 지키는 입력만 주어진다.

출력

첫째 줄에 E S M으로 표시되는 가장 빠른 연도를 출력한다. 1 1 1은 항상 1이기 때문에, 정답이 음수가 나오는 경우는 없다.

코드

# 1476

import sys
e, s, m = map(int,sys.stdin.readline().split())
cnt = 1
starte, starts, startm = 1,1,1
while True:
    if starte == e and starts == s and startm == m:
        break
    starte += 1
    starts += 1
    startm += 1
    cnt += 1
    if starte > 15:
        starte = 1
    if starts > 28:
        starts = 1
    if startm > 19:
        startm = 1

print(cnt)

풀이

1 1 1 을 1년 지날 때마다 모두 +1 해주며 e, s, m 값과 같아질 때까지 cnt+=1 해준다.

+1 해줄 때, e,s,m 의 범위 넘으면 다시 1로 초기화해준다.

728x90

문제

상근이는 어렸을 적에 "봄보니 (Bomboni)" 게임을 즐겨했다.

가장 처음에 N×N크기에 사탕을 채워 놓는다. 사탕의 색은 모두 같지 않을 수도 있다. 상근이는 사탕의 색이 다른 인접한 두 칸을 고른다. 그 다음 고른 칸에 들어있는 사탕을 서로 교환한다. 이제, 모두 같은 색으로 이루어져 있는 가장 긴 연속 부분(행 또는 열)을 고른 다음 그 사탕을 모두 먹는다.

사탕이 채워진 상태가 주어졌을 때, 상근이가 먹을 수 있는 사탕의 최대 개수를 구하는 프로그램을 작성하시오.

입력

첫째 줄에 보드의 크기 N이 주어진다. (3 ≤ N ≤ 50)

다음 N개 줄에는 보드에 채워져 있는 사탕의 색상이 주어진다. 빨간색은 C, 파란색은 P, 초록색은 Z, 노란색은 Y로 주어진다.

사탕의 색이 다른 인접한 두 칸이 존재하는 입력만 주어진다.

출력

첫째 줄에 상근이가 먹을 수 있는 사탕의 최대 개수를 출력한다.

코드

# 3085

import sys
n = int(sys.stdin.readline())
arr = [list(sys.stdin.readline().strip()) for _ in range(n)]
answer = 0

# 완전 탐색
def check(array):
    max_len = 1 # 함수의 리턴 값 -> 가장 긴 최대 길이
    for i in range(n):
        # 열 비교
        cnt = 1 # 같은 색인 최대 길이
        for j in range(1,n):
            if arr[i][j] == arr[i][j-1]:
                cnt += 1
            else: # 인접한 사탕 중 다른 색 나오면 cnt 초기화
                cnt = 1
            max_len = max(max_len, cnt) # max_len 갱신
        
        # 행 비교
        cnt = 1  # 같은 색인 최대 길이
        for j in range(1,n):
            if arr[j][i] == arr[j-1][i]:
                cnt += 1
            else:
                cnt = 1
            max_len = max(max_len, cnt)  # max_len 갱신
    return max_len

# 인접하고 색 다른 두 칸 고르고 완탐 호출
for i in range(n):
    for j in range(n):
        if j+1<n: # 인접한 열 끼리 비교 후 교체
            if arr[i][j] != arr[i][j+1]:
                arr[i][j],arr[i][j+1] = arr[i][j+1], arr[i][j]
                # 완전탐색 수행
                tmp = check(arr)
                # 정답과 완탐 CNT 비교
                answer = max(answer,tmp)
                # 교체 한 것 다시 원래대로 돌려놓기 ( 모든 경우의수 비교해야함)
                arr[i][j], arr[i][j + 1] = arr[i][j + 1], arr[i][j]

        if i+1<n: # 인접한 행 끼리 비교 후 교체
            if arr[i][j] != arr[i+1][j]:
                arr[i][j], arr[i + 1][j] = arr[i + 1][j],arr[i][j]
                # 완전탐색 수행
                tmp = check(arr)
                # 정답과 완탐 CNT 비교
                answer = max(answer, tmp)
                # 교체 한 것 다시 원래대로 돌려놓기 ( 모든 경우의수 비교해야함)
                arr[i][j], arr[i + 1][j] = arr[i + 1][j], arr[i][j]
print(answer)

풀이

보드의 크기 N이 주어진다. (3 ≤ N ≤ 50) -> 완전 탐색 가능하다.

 

1. 색이 다른 인접한 두 사탕 선택 후 교체

2. 교체한 배열에서 같은 사탕 색이 있는 (행 또는 열) 최대 길이 구하기

3. 교체한 사탕 다시 제자리로 위치시키고 다음 인접한 사탕 교체 후 완전탐색 반복

 

계속 교체할 사탕 2개 선택해서 자리 바꾸고 완탐으로 최대 길이 구하고 리턴 시켜서

answer 값을 max 값으로 갱신시킨다.

 

이 문제 괜찮은 것 같다.

나중에 다시 풀어보자.

 

728x90

문제

방향 없는 그래프가 주어졌을 때, 연결 요소 (Connected Component)의 개수를 구하는 프로그램을 작성하시오.

입력

첫째 줄에 정점의 개수 N과 간선의 개수 M이 주어진다. (1 ≤ N ≤ 1,000, 0 ≤ M ≤ N×(N-1)/2) 둘째 줄부터 M개의 줄에 간선의 양 끝점 u와 v가 주어진다. (1 ≤ u, v ≤ N, u ≠ v) 같은 간선은 한 번만 주어진다.

출력

첫째 줄에 연결 요소의 개수를 출력한다.

풀이 1 (DFS)

# 11724
import sys
sys.setrecursionlimit(10000)
n,m = map(int,sys.stdin.readline().split())
graph = [[] for _ in range(n+1)]
visited = [0]*(n+1)
cnt = 0
for _ in range(m):
    u,v = map(int,sys.stdin.readline().split())
    graph[u].append(v)
    graph[v].append(u)
# print(graph)

def dfs(node):
    visited[node] = 1
    for i in graph[node]:
        if not visited[i]:
            dfs(i)

for i in range(1,n+1):
    if not visited[i]:
        dfs(i)
        cnt += 1
print(cnt)

풀이 2 (BFS)

# 11724
import sys
# sys.setrecursionlimit(10000)
from collections import deque
n,m = map(int,sys.stdin.readline().split())
graph = [[] for _ in range(n+1)]
visited = [0]*(n+1)
cnt = 0
for _ in range(m):
    u,v = map(int,sys.stdin.readline().split())
    graph[u].append(v)
    graph[v].append(u)
# print(graph)

def bfs(graph, node, visited):
    visited[node] = 1
    q = deque([node])
    while q:
        v = q.popleft()
        for i in graph[v]:
            if not visited[i]:
                q.append(i)
                visited[i] = 1

for i in range(1,n+1):
    if not visited[i]:
        bfs(graph, i, visited)
        cnt += 1
print(cnt)

 

+ Recent posts