//
728x90
반응형

BOJ 4949 균형잡힌 세상

문제

세계는 균형이 잘 잡혀있어야 한다. 양과 음, 빛과 어둠 그리고 왼쪽 괄호와 오른쪽 괄호처럼 말이다.

정민이의 임무는 어떤 문자열이 주어졌을 때, 괄호들의 균형이 잘 맞춰져 있는지 판단하는 프로그램을 짜는 것이다.

문자열에 포함되는 괄호는 소괄호("()") 와 대괄호("[]")로 2종류이고, 문자열이 균형을 이루는 조건은 아래와 같다.

    모든 왼쪽 소괄호("(")는 오른쪽 소괄호(")")와만 짝을 이뤄야 한다.
    모든 왼쪽 대괄호("[")는 오른쪽 대괄호("]")와만 짝을 이뤄야 한다.
    모든 오른쪽 괄호들은 자신과 짝을 이룰 수 있는 왼쪽 괄호가 존재한다.
    모든 괄호들의 짝은 1:1 매칭만 가능하다. 즉, 괄호 하나가 둘 이상의 괄호와 짝지어지지 않는다.
    짝을 이루는 두 괄호가 있을 때, 그 사이에 있는 문자열도 균형이 잡혀야 한다.
    
정민이를 도와 문자열이 주어졌을 때 균형잡힌 문자열인지 아닌지를 판단해보자.

시간 제한 : 1 초 
메모리 제한: 128 MB

입력

하나 또는 여러줄에 걸쳐서 문자열이 주어진다. 

각 문자열은 영문 알파벳, 공백, 소괄호("( )") 대괄호("[ ]")등으로 이루어져 있으며, 

길이는 100글자보다 작거나 같다. 각 줄은 마침표(".")로 끝난다.

입력의 종료조건으로 맨 마지막에 점 하나(".")가 들어온다.

출력

각 줄마다 해당 문자열이 균형을 이루고 있으면 "yes"를, 아니면 "no"를 출력한다.

예제 입력 1

So when I die (the [first] I will see in (heaven) is a score list).
[ first in ] ( first out ).
Half Moon tonight (At least it is better than no Moon at all].
A rope may form )( a trail in a maze.
Help( I[m being held prisoner in a fortune cookie factory)].
([ (([( [ ] ) ( ) (( ))] )) ]).
 .
.

예제 출력 1

yes
yes
no
no
no
yes
yes

힌트

7번째의 " ."와 같이 괄호가 하나도 없는 경우도 균형잡힌 문자열로 간주할 수 있다.

풀이

import sys

input = sys.stdin.readline
while True :
    s = input().rstrip()
    stack = []

    if s == "." :
        break

    for i in s :
        if i == '[' or i == '(' :
            stack.append(i)
        elif i == ']' :
            if len(stack) != 0 and stack[-1] == '[' :
                stack.pop() 
            else : 
                stack.append(']')
                break
        elif i == ')' :
            if len(stack) != 0 and stack[-1] == '(' :
                stack.pop()
            else :
                stack.append(')')
                break
    if len(stack) == 0 :
        print('yes')
    else :
        print('no')
728x90
반응형
728x90
반응형

BOJ 1874

문제

스택 (stack)은 기본적인 자료구조 중 하나로, 컴퓨터 프로그램을 작성할 때 자주 이용되는 개념이다.

스택은 자료를 넣는 (push) 입구와 자료를 뽑는 (pop) 입구가 같아 제일 나중에 들어간 자료가 

제일 먼저 나오는 (LIFO, Last in First out) 특성을 가지고 있다.

1부터 n까지의 수를 스택에 넣었다가 뽑아 늘어놓음으로써, 하나의 수열을 만들 수 있다. 

이때, 스택에 push하는 순서는 반드시 오름차순을 지키도록 한다고 하자. 

임의의 수열이 주어졌을 때 스택을 이용해 그 수열을 만들 수 있는지 없는지,

있다면 어떤 순서로 push와 pop 연산을 수행해야 하는지를 알아낼 수 있다. 

이를 계산하는 프로그램을 작성하라.

시간 제한 : 2 초
메모리 제한 : 128 MB

입력

첫 줄에 n (1 ≤ n ≤ 100,000)이 주어진다. 

둘째 줄부터 n개의 줄에는 수열을 이루는 1이상 n이하의 정수가 하나씩 순서대로 주어진다.

물론 같은 정수가 두 번 나오는 일은 없다.

출력

입력된 수열을 만들기 위해 필요한 연산을 한 줄에 한 개씩 출력한다. 

push연산은 +로, pop 연산은 -로 표현하도록 한다. 

불가능한 경우 NO를 출력한다.

예제 입력 1

8
4
3
6
8
7
5
2
1

예제 출력 1

+
+
+
+
-
-
+
+
-
+
+
-
-
-
-
-

예제 입력 2

5
1
2
5
3
4

예제 출력 2

NO

힌트

1부터 n까지에 수에 대해 차례로 

[push, push, push, push, pop, pop, push, push, pop, push, push, pop, pop, pop, pop, pop] 

연산을 수행하면 수열 [4, 3, 6, 8, 7, 5, 2, 1]을 얻을 수 있다.

풀이

import sys

input = sys.stdin.readline
n = int(input())
num_list = [int(input()) for _ in range(n)]
 
stack = [] 
res = [] 
no_res = True 
cnt = 0
 
for i in num_list:
    
    while cnt < i:
        cnt += 1
        stack.append(cnt)
        res.append('+')
        
    if stack[-1] == i:
        stack.pop()
        res.append('-')
    else:
        no_res = False
        break
    
if no_res == False:
    print('NO')
else:
    print('\n'.join(res))

 

728x90
반응형
728x90
반응형

BOJ 10773 제로

문제

나코더 기장 재민이는 동아리 회식을 준비하기 위해서 장부를 관리하는 중이다.

재현이는 재민이를 도와서 돈을 관리하는 중인데, 

애석하게도 항상 정신없는 재현이는 돈을 실수로 잘못 부르는 사고를 치기 일쑤였다.

재현이는 잘못된 수를 부를 때마다 0을 외쳐서, 가장 최근에 재민이가 쓴 수를 지우게 시킨다.

재민이는 이렇게 모든 수를 받아 적은 후 그 수의 합을 알고 싶어 한다. 재민이를 도와주자!

시간 제한 : 1 초
메모리 제한 : 256 MB

입력

첫 번째 줄에 정수 K가 주어진다. (1 ≤ K ≤ 100,000)

이후 K개의 줄에 정수가 1개씩 주어진다. 

정수는 0에서 1,000,000 사이의 값을 가지며, 

정수가 "0" 일 경우에는 가장 최근에 쓴 수를 지우고, 아닐 경우 해당 수를 쓴다.

정수가 "0"일 경우에 지울 수 있는 수가 있음을 보장할 수 있다.

출력

재민이가 최종적으로 적어 낸 수의 합을 출력한다. 

최종적으로 적어낸 수의 합은 231-1보다 작거나 같은 정수이다.

예제 입력 1

4
3
0
4
0

예제 출력 1

0

예제 입력 2

10
1
3
5
4
0
0
7
0
0
6

예제 출력 2

7

풀이

import sys

input = sys.stdin.readline
k = int(input())
zero = []

for i in range(k):
    num = int(input())
    if num == 0:
        zero.pop()
    else:
        zero.append(num)

print(sum(zero))
728x90
반응형
728x90
반응형

BOJ 10828 스택

문제

정수를 저장하는 스택을 구현한 다음, 입력으로 주어지는 명령을 처리하는 프로그램을 작성하시오.

명령은 총 다섯 가지이다.

push X: 정수 X를 스택에 넣는 연산이다.
pop: 스택에서 가장 위에 있는 정수를 빼고, 그 수를 출력한다. 
	만약 스택에 들어있는 정수가 없는 경우에는 -1을 출력한다.
size: 스택에 들어있는 정수의 개수를 출력한다.
empty: 스택이 비어있으면 1, 아니면 0을 출력한다.
top: 스택의 가장 위에 있는 정수를 출력한다. 
	만약 스택에 들어있는 정수가 없는 경우에는 -1을 출력한다.
    
시간 제한 : 0.5 초(추가 시간 없음)
메모리 제한 : 256 MB

입력

첫째 줄에 주어지는 명령의 수 N (1 ≤ N ≤ 10,000)이 주어진다.

둘째 줄부터 N개의 줄에는 명령이 하나씩 주어진다.

주어지는 정수는 1보다 크거나 같고, 100,000보다 작거나 같다.

문제에 나와있지 않은 명령이 주어지는 경우는 없다.

출력

출력해야하는 명령이 주어질 때마다, 한 줄에 하나씩 출력한다.

예제 입력 1

14
push 1
push 2
top
size
empty
pop
pop
pop
size
empty
pop
push 3
empty
top

예제 출력 1

2
2
0
2
1
-1
0
1
-1
0
3

예제 입력 2

7
pop
top
push 123
top
pop
top
pop

예제 출력 2

-1
-1
123
123
-1
-1

풀이

import sys

input = sys.stdin.readline
n = int(input())
stack = []

for _ in range(n):
    command = input().split()
    
    if command[0] == 'push':
        stack.append(int(command[1]))
    elif command[0] == 'pop':
        if stack:
            print(stack.pop())
        else:
            print(-1)
    elif command[0] == 'size':
        print(len(stack))
    elif command[0] == 'empty':
        if stack:
            print(0)
        else:
            print(1)
    elif command[0] == 'top':
        if stack:
            print(stack[-1])
        else:
            print(-1)
728x90
반응형
728x90
반응형

BOJ 9012 괄호

문제

괄호 문자열(Parenthesis String, PS)은 두 개의 괄호 기호인 ‘(’ 와 ‘)’ 만으로 구성되어 있는 문자열이다. 

그 중에서 괄호의 모양이 바르게 구성된 문자열을 올바른 괄호 문자열(Valid PS, VPS)이라고 부른다. 

한 쌍의 괄호 기호로 된 “( )” 문자열은 기본 VPS 이라고 부른다. 

만일 x 가 VPS 라면 이것을 하나의 괄호에 넣은 새로운 문자열 “(x)”도 VPS 가 된다. 

그리고 두 VPS x 와 y를 접합(concatenation)시킨 새로운 문자열 xy도 VPS 가 된다. 

예를 들어 “(())()”와 “((()))” 는 VPS 이지만 “(()(”, “(())()))” , 그리고 “(()” 는 모두 VPS 가 아닌 문자열이다. 

여러분은 입력으로 주어진 괄호 문자열이 VPS 인지 아닌지를 판단해서 그 결과를 YES 와 NO 로 나타내어야 한다. 

시간 제한 : 1 초
메모리 제한 : 128 MB

입력

입력 데이터는 표준 입력을 사용한다. 입력은 T개의 테스트 데이터로 주어진다.

입력의 첫 번째 줄에는 입력 데이터의 수를 나타내는 정수 T가 주어진다.

각 테스트 데이터의 첫째 줄에는 괄호 문자열이 한 줄에 주어진다. 

하나의 괄호 문자열의 길이는 2 이상 50 이하이다.

출력

출력은 표준 출력을 사용한다. 

만일 입력 괄호 문자열이 올바른 괄호 문자열(VPS)이면 “YES”, 아니면 “NO”를 한 줄에 하나씩 차례대로 출력해야 한다.

예제 입력 1

6
(())())
(((()())()
(()())((()))
((()()(()))(((())))()
()()()()(()()())()
(()((())()(

예제 출력 1

NO
NO
YES
NO
YES
NO

예제 입력 2

3
((
))
())(()

예제 출력 2

NO
NO
NO

풀이

import sys

input = sys.stdin.readline
t = int(input())

def check(stack):
    cnt = 0
    while stack:
        vps = stack.pop()
        if vps == ')':
            cnt += 1
        else:
            if cnt <= 0:
                return False
            cnt -= 1
    if cnt != 0:
        return False
    return True

for _ in range(t):
    stack = list(input().rstrip())
    if check(stack):
        print('YES')
    else:
        print('NO')
728x90
반응형
728x90
반응형

BOJ 2630 색종이 만들기

문제

아래 <그림 1>과 같이 여러개의 정사각형칸들로 이루어진 정사각형 모양의 종이가 주어져 있고, 

각 정사각형들은 하얀색으로 칠해져 있거나 파란색으로 칠해져 있다. 

주어진 종이를 일정한 규칙에 따라 잘라서 다양한 크기를 가진 정사각형 모양의 하얀색 또는 파란색 색종이를 만들려고 한다.

출처 - 백준온라인저지

전체 종이의 크기가 N×N(N=2k, k는 1 이상 7 이하의 자연수) 이라면 종이를 자르는 규칙은 다음과 같다.

전체 종이가 모두 같은 색으로 칠해져 있지 않으면 가로와 세로로 중간 부분을 잘라서 

<그림 2>의 I, II, III, IV와 같이 똑같은 크기의 네 개의 N/2 × N/2색종이로 나눈다. 

나누어진 종이 I, II, III, IV 각각에 대해서도 앞에서와 마찬가지로 모두 같은 색으로 칠해져 있지 않으면 

같은 방법으로 똑같은 크기의 네 개의 색종이로 나눈다. 

이와 같은 과정을 잘라진 종이가 모두 하얀색 또는 모두 파란색으로 칠해져 있거나, 

하나의 정사각형 칸이 되어 더 이상 자를 수 없을 때까지 반복한다.

위와 같은 규칙에 따라 잘랐을 때 <그림 3>은 <그림 1>의 종이를 처음 나눈 후의 상태를, 

<그림 4>는 두 번째 나눈 후의 상태를, 

<그림 5>는 최종적으로 만들어진 다양한 크기의 9장의 하얀색 색종이와 7장의 파란색 색종이를 보여주고 있다.

출처 - 백준온라인저지

입력으로 주어진 종이의 한 변의 길이 N과 각 정사각형칸의 색(하얀색 또는 파란색)이 주어질 때 

잘라진 하얀색 색종이와 파란색 색종이의 개수를 구하는 프로그램을 작성하시오.

시간 제한 : 1 초
메모리 제한 : 128 MB

입력

첫째 줄에는 전체 종이의 한 변의 길이 N이 주어져 있다. 

N은 2, 4, 8, 16, 32, 64, 128 중 하나이다. 

색종이의 각 가로줄의 정사각형칸들의 색이 윗줄부터 차례로 둘째 줄부터 마지막 줄까지 주어진다. 

하얀색으로 칠해진 칸은 0, 파란색으로 칠해진 칸은 1로 주어지며, 각 숫자 사이에는 빈칸이 하나씩 있다.

출력

첫째 줄에는 잘라진 햐얀색 색종이의 개수를 출력하고, 둘째 줄에는 파란색 색종이의 개수를 출력한다.

예제 입력 1

8
1 1 0 0 0 0 1 1
1 1 0 0 0 0 1 1
0 0 0 0 1 1 0 0
0 0 0 0 1 1 0 0
1 0 0 0 1 1 1 1
0 1 0 0 1 1 1 1
0 0 1 1 1 1 1 1
0 0 1 1 1 1 1 1

예제 출력 1

9
7

풀이

import sys

input = sys.stdin.readline
n = int(input())
paper = [list(map(int, input().split())) for _ in range(n)] 
res = []

def recursive(x, y, n) :
  color = paper[x][y]

  for i in range(x, x+n) :
    for j in range(y, y+n) :
      if color != paper[i][j] :
        recursive(x, y, n//2)
        recursive(x, y+n//2, n//2)
        recursive(x+n//2, y, n//2)
        recursive(x+n//2, y+n//2, n//2)
        return

  if color == 0 :
    res.append(0)
  else :
    res.append(1)


recursive(0, 0, n)
print(res.count(0))
print(res.count(1))
728x90
반응형
728x90
반응형

BOJ 3040 백설 공주와 일곱 난쟁이

문제

매일 매일 일곱 난쟁이는 광산으로 일을 하러 간다. 

난쟁이가 일을 하는 동안 백설공주는 그들을 위해 저녁 식사를 준비한다. 

백설공주는 의자 일곱개, 접시 일곱개, 나이프 일곱개를 준비한다.

어느 날 광산에서 아홉 난쟁이가 돌아왔다. 

(왜 그리고 어떻게 아홉 난쟁이가 돌아왔는지는 아무도 모른다) 

아홉 난쟁이는 각각 자신이 백설공주의 일곱 난쟁이라고 우기고 있다.

백설공주는 이런 일이 생길 것을 대비해서, 

난쟁이가 쓰고 다니는 모자에 100보다 작은 양의 정수를 적어 놓았다. 

사실 백설 공주는 공주가 되기 전에 매우 유명한 수학자였다. 

따라서, 일곱 난쟁이의 모자에 쓰여 있는 숫자의 합이 100이 되도록 적어 놓았다.

아홉 난쟁이의 모자에 쓰여 있는 수가 주어졌을 때, 일곱 난쟁이를 찾는 프로그램을 작성하시오. 

(아홉 개의 수 중 합이 100이 되는 일곱 개의 수를 찾으시오)

시간 제한 : 1 초
메모리 제한 : 128 MB

입력

총 아홉개 줄에 1보다 크거나 같고 99보다 작거나 같은 자연수가 주어진다. 

모든 숫자는 서로 다르다.

또, 항상 답이 유일한 경우만 입력으로 주어진다.

출력

일곱 난쟁이가 쓴 모자에 쓰여 있는 수를 한 줄에 하나씩 출력한다.

예제 입력 1

7
8
10
13
15
19
20
23
25

예제 출력 1

7
8
10
13
19
20
23

예제 입력 2

8
6
5
1
37
30
28
22
36

예제 출력 2

8
6
5
1
30
28
22

풀이

import sys

input = sys.stdin.readline
arr = [int(input()) for _ in range(9)]

for i in range(8):
    for j in range(i + 1, 9):
        res = 0

        for k in range(9):
            if k == i or k == j:
                continue
            res += arr[k]
            
        if res == 100:
            for k in range(9):
                if k == i or k == j:
                    continue
                print(arr[k])
            exit()
728x90
반응형
728x90
반응형

BOJ 16435 스네이크버드

문제

스네이크버드는 뱀과 새의 모습을 닮은 귀여운 생물체입니다. 

스네이크버드의 주요 먹이는 과일이며 과일 하나를 먹으면 길이가 1만큼 늘어납니다.

과일들은 지상으로부터 일정 높이를 두고 떨어져 있으며 i (1 ≤ i ≤ N) 번째 과일의 높이는 hi입니다. 

스네이크버드는 자신의 길이보다 작거나 같은 높이에 있는 과일들을 먹을 수 있습니다.

스네이크버드의 처음 길이가 L일때 과일들을 먹어 늘릴 수 있는 최대 길이를 구하세요.

시간 제한 : 1 초
메모리 제한 : 128 MB

입력

첫 번째 줄에 과일의 개수 N (1 ≤ N ≤ 1,000) 과 스네이크버드의 초기 길이 정수 L (1 ≤ L ≤ 10,000) 이 주어집니다.

두 번째 줄에는 정수 h1, h2, ..., hN (1 ≤ hi ≤ 10,000) 이 주어집니다.

출력

첫 번째 줄에 스네이크버드의 최대 길이를 출력합니다.

예제 입력 1

3 10
10 11 13

예제 출력 1

12

스네이크버드의 처음 길이는 10이며 1번 과일을 먹은 후 길이가 11이 됩니다. 

이후 2번 과일을 먹으면 길이가 12가 됩니다. 

더 이상 먹을 수 있는 과일이 없으므로 최대 길이는 12가 됩니다.

예제 입력 2

9 1
9 5 8 1 3 2 7 6 4

예제 출력 2

10

풀이

n, l=map(int, input().split())
h = list(map(int, input().split()))

h.sort()

for i in range(n):
    if l>=h[i]:
        l+=1
print(l)
728x90
반응형

+ Recent posts