20200318 알고리즘

1. 중복순열 구하기

1부터 N까지 번호가 적힌 구슬이 있습니다. 이 중 중복을 허락하여 M번을 뽑아 일렬로 나열 하는 방법을 모두 출력합니다.

▣ 입력설명 첫 번째 줄에 자연수 N(3<=N<=10)과 M(3<=M<=N) 이 주어집니다.

▣ 출력설명 첫 번째 줄에 결과를 출력합니다. 맨 마지막 총 경우의 수를 출력합니다. 출력순서는 사전순으로 오름차순으로 출력합니다.

▣ 입력예제 1

3 2

▣ 출력예제 1

1 1
1 2
1 3
2 1
2 2
2 3
3 1
3 2 
3 3
9

Solution

import sys
sys.stdin = open("input50.txt", "rt")

def DFS(L):
    global cnt
    if L == m:
        cnt += 1
        for v in a:
            print(v, end=' ')
        print()
    else:
        for i in range(1, n+1):
            a[L] = i
            DFS(L+1)

if __name__ == '__main__':
    n, m = map(int, input().split())
    a = [0] * m
    cnt = 0
    DFS(0)
    print(cnt)

2. 동전교환

다음과 같이 여러 단위의 동전들이 주어져 있을때 거스름돈을 가장 적은 수의 동전으로 교환 해주려면 어떻게 주면 되는가? 각 단위의 동전은 무한정 쓸 수 있다.

▣ 입력설명 첫 번째 줄에는 동전의 종류개수 N(1<=N<=12)이 주어진다. 두 번째 줄에는 N개의 동전의 종 류가 주어지고, 그 다음줄에 거슬러 줄 금액 M(1<=M<=500)이 주어진다. 각 동전의 종류는 100원을 넘지 않는다.

▣ 출력설명 첫 번째 줄에 거슬러 줄 동전의 최소개수를 출력한다.

▣ 입력예제 1

3
1 2 5
15

▣ 출력예제 1

3

Solution

import sys
sys.stdin = open("input51.txt", "rt")

def DFS(L, sum):
    global min
    if L >= min:
        return
    if sum > t:
        return
    if sum == t:
        if min > L:
            min = L
        return
    else:
        for i in range(n):
            DFS(L+1, sum + a[i])

if __name__ == '__main__':
    n = int(input())
    a = list(map(int, input().split()))
    a.sort(reverse=True)
    t = int(input())
    min = 2147000000
    DFS(0, 0)
    print(min)

3. 순열 구하기

1부터N까지번호가적힌구슬이있습니다.이중 M개를뽑아일렬로나열하는방법을모두 출력합니다.

▣ 입력설명 첫 번째 줄에 자연수 N(3<=N<=10)과 M(3<=M<=N) 이 주어집니다.

▣ 출력설명 첫 번째 줄에 결과를 출력합니다. 맨 마지막 총 경우의 수를 출력합니다. 출력순서는 사전순으로 오름차순으로 출력합니다.

▣ 입력예제 1

3 2

▣ 출력예제 1

1 2
1 3
2 1
2 3
3 1
3 2
6

Solution

import sys
sys.stdin = open("input52.txt", "rt")

def DFS(L):
    global cnt
    if L == m:
        for i in range(L):
            print(res[i], end=' ')
        cnt += 1
        print()
    else:
        for j in range(1, n+1):
            if ch[j] == 0:
                ch[j] = 1
                res[L] = j
                DFS(L+1)
                ch[j] = 0


if __name__ == '__main__':
    n, m = map(int, input().split())
    ch = [0] * (n + 1)
    res = [0] * m
    cnt = 0
    DFS(0)
    print(cnt)

4. 수열 추측하기

가장 윗줄에 1부터 N까지의 숫자가 한 개씩 적혀 있다. 그리고 둘째 줄부터 차례대로 파스칼 의 삼각형처럼 위의 두개를 더한 값이 저장되게 된다. 예를 들어 N이 4 이고 가장 윗 줄에 3 1 2 4 가 있다고 했을 때, 다음과 같은 삼각형이 그려진다.

image

N과 가장 밑에 있는 숫자가 주어져 있을 때 가장 윗줄에 있는 숫자를 구하는 프로그램을 작성하 시오. 단, 답이 여러가지가 나오는 경우에는 사전순으로 가장 앞에 오는 것을 출력하여야 한다.

▣ 입력설명 첫째 줄에 두개의 정수 N(1≤N≤10)과 F가 주어진다. N은 가장 윗줄에 있는 숫자의 개수를 의 미하며 F는 가장 밑에 줄에 있는 수로 1,000,000 이하이다.

▣ 출력설명 첫째 줄에 삼각형에서 가장 위에 들어갈 N개의 숫자를 빈 칸을 사이에 두고 출력한다. 답이 존재 하지 않는 경우는 입력으로 주어지지 않는다.

▣ 입력예제 1

4 16

▣ 출력예제 1

3 1 2 4

Solution

import sys
sys.stdin = open("input53.txt", "rt")

def DFS(L, sum):
    if L == n and sum == m:
        for v in p:
            print(v, end=' ')
        sys.exit(0)
    else:
        for i in range(1, n+1):
            if ch[i] == 0:
                ch[i] = 1
                p[L] = i
                DFS(L+1, sum + (p[L] * b[L]))
                ch[i] = 0


if __name__ == '__main__':
    n, m = map(int, input().split())
    p = [0]*n
    b = [1]*n
    ch = [0] * (n+1)
    for i in range(1, n):
        b[i] = b[i-1] * (n-i) // i
    DFS(0, 0)

5. 조합 만들기

1부터N까지번호가적힌구슬이있습니다.이중 M개를뽑는방법의수를출력하는프로그 램을 작성하세요.

▣ 입력설명 첫 번째 줄에 자연수 N(3<=N<=10)과 M(3<=M<=N) 이 주어집니다.

▣ 출력설명 첫 번째 줄에 결과를 출력합니다. 맨 마지막 총 경우의 수를 출력합니다. 출력순서는 사전순으로 오름차순으로 출력합니다.

▣ 입력예제 1

4 2

▣ 출력예제 1

1 2
1 3
1 4
2 3
2 4
3 4
6

Solution

import sys
sys.stdin = open("input54.txt", "rt")


def DFS(L, s):
    global cnt
    if L == m:
        for j in range(m):
            print(res[j], end=' ')
        print()
        cnt += 1
        return
    if s > n:
        return
    else:
        for i in range(s, n+1):
            res[L] = i
            DFS(L+1, i+1)

if __name__ == '__main__':
    n, m = map(int, input().split())
    cnt = 0
    res = [0] * m
    DFS(0, 1)
    print(cnt)

Written by@[HongDongUk]
공부한 것을 소소하게 적는 블로그.

GitHubFacebook