[문제해결 - 자료구조] BOJ1406 / 에디터 / 실버2 (Python, 파이썬)

oldshoe·2025년 2월 4일
0

알고리즘 문제

목록 보기
23/23

백준1406 문제 보러가기

문제

한 줄로 된 간단한 에디터를 구현하려고 한다. 이 편집기는 영어 소문자만을 기록할 수 있는 편집기로, 최대 600,000글자까지 입력할 수 있다.

이 편집기에는 '커서'라는 것이 있는데, 커서는 문장의 맨 앞(첫 번째 문자의 왼쪽), 문장의 맨 뒤(마지막 문자의 오른쪽), 또는 문장 중간 임의의 곳(모든 연속된 두 문자 사이)에 위치할 수 있다. 즉 길이가 L인 문자열이 현재 편집기에 입력되어 있으면, 커서가 위치할 수 있는 곳은 L+1가지 경우가 있다.

이 편집기가 지원하는 명령어는 다음과 같다.

초기에 편집기에 입력되어 있는 문자열이 주어지고, 그 이후 입력한 명령어가 차례로 주어졌을 때, 모든 명령어를 수행하고 난 후 편집기에 입력되어 있는 문자열을 구하는 프로그램을 작성하시오. 단, 명령어가 수행되기 전에 커서는 문장의 맨 뒤에 위치하고 있다고 한다.

입력

첫째 줄에는 초기에 편집기에 입력되어 있는 문자열이 주어진다. 이 문자열은 길이가 N이고, 영어 소문자로만 이루어져 있으며, 길이는 100,000을 넘지 않는다. 둘째 줄에는 입력할 명령어의 개수를 나타내는 정수 M(1 ≤ M ≤ 500,000)이 주어진다. 셋째 줄부터 M개의 줄에 걸쳐 입력할 명령어가 순서대로 주어진다. 명령어는 위의 네 가지 중 하나의 형태로만 주어진다.

출력

첫째 줄에 모든 명령어를 수행하고 난 후 편집기에 입력되어 있는 문자열을 출력한다.

예제 입력 1

abcd
3
P x
L
P y

예제 출력 1

abcdyx

예제 입력 2

abc
9
L
L
L
L
L
P x
L
B
P y

예제 출력 2

yxabc

예제 입력 3

dmih
11
B
B
P x
L
B
B
B
P y
D
D
P z

예제 출력 3

yxz

문제 해결 과정

간단하게(?) 구현하면 되는 문제인 줄 알았다.
입력된 문자열 길이를 재고 위의 조건에 맞게 커서를 이동시켜서 요소를 넣으면 된다고 생각했다.

in_value = list(input())
i = len(in_value)
M = int(input())

for _ in range(M) :
    command = input()

    if command[0] == 'L' :
        if i != 0:
            i -= 1
        else : continue
    elif command[0] == 'D' :
        i += 1
    elif command[0] == 'B' :
        if i != 0 :
            del in_value[i-1]
            i -= 1
        else : continue
    elif command[0] == 'P' :
        in_value.insert(i, command[2])
        i += 1
        
print(''.join(in_value))

이렇게 하니 시간초과가 떴다.
그래서 블로그 하나를 참고했는데 다들 참신한 방법으로 구현했다.
스택(파이썬에서는 리스트)을 두 개를 만들어서 커서를 이동할 때마다 좌, 우 스택에 이동시키는 것이었다.

예를 들어, 현재 입력된 문자열은 ABCD라고 하면 일단 왼쪽에 ABCD가 있고 오른쪽에 빈 리스트가 있다.

[ABCD] / []

이 때 P 명령어가 들어와 문자를 입력하면 왼쪽에 입력해야하기 때문에 아래와 같이 된다.

[ABCDX] / []

그리고 L이 들어오면 커서를 왼쪽으로 옮겨야한다.
그래서 왼쪽 끝에 있는 요소를 pop하여 오른쪽으로 옮긴다.
[ABCD] / [X]

반대로 D가 들어오면 반대로 하면 된다.
오른쪽 끝에 있는 요소를 pop하여 오른쪽으로 들어온다.

B가 들어오면 왼쪽 문자를 삭제하면 되어서 왼쪽 리스트의 요소를 pop하여 삭제한다.

최종 코드

from sys import stdin

left = list(input())
right = []

for _ in range(int(input())):
    command = list(stdin.readline().split())
    if command[0] == 'L' and left:
        right.append(left.pop())
    elif command[0] == 'D' and right:
        left.append(right.pop())
    elif command[0] == 'B' and left:
        left.pop()
    elif command[0] == 'P':
        left.append(command[1])

answer = left + right[::-1]
print(''.join(answer))

참고 블로그

https://corin-e.tistory.com/entry/%EB%B0%B1%EC%A4%80-1406-%EC%97%90%EB%94%94%ED%84%B0-%ED%8C%8C%EC%9D%B4%EC%8D%AC

profile
toomuxi : There are many things in the world that I want to do

0개의 댓글

관련 채용 정보