상세 컨텐츠

본문 제목

백준 15552 - 빠른 A+B / sys.stdin.readline() (파이썬)

Tech/백준 단계별 문제

by 2020. 4. 28. 23:51

본문

조금 더 빠른 입력 방법을 알려주는 문제입니다.

알고리즘 문제를 풀 때 시간도 중요하게 작용하기 때문에 꼭 알고있어야할 문제입니다!

이해하기 어려울 수도 있는데 차근차근 가봅시당~

 

https://www.acmicpc.net/problem/15552

 

15552번: 빠른 A+B

첫 줄에 테스트케이스의 개수 T가 주어진다. T는 최대 1,000,000이다. 다음 T줄에는 각각 두 정수 A와 B가 주어진다. A와 B는 1 이상, 1,000 이하이다.

www.acmicpc.net

다음은 백준 문제 설명으로 나와있는 내용입니다.

본격적으로 for문 문제를 풀기 전에 주의해야 할 점이 있다. 입출력 방식이 느리면 여러 줄을 입력받거나 출력할 때 시간초과가 날 수 있다는 점이다. C++을 사용하고 있고 cin/cout을 사용하고자 한다면, cin.tie(NULL)과 sync_with_stdio(false)를 둘 다 적용해 주고, endl 대신 개행문자(\n)를 쓰자. 단, 이렇게 하면 더 이상 scanf/printf/puts/getchar/putchar 등 C의 입출력 방식을 사용하면 안 된다. Java를 사용하고 있다면, Scanner와 System.out.println 대신 BufferedReader와 BufferedWriter를 사용할 수 있다. BufferedWriter.flush는 맨 마지막에 한 번만 하면 된다. Python을 사용하고 있다면, input 대신 sys.stdin.readline을 사용할 수 있다. 단, 이때는 맨 끝의 개행문자까지 같이 입력받기 때문에 문자열을 저장하고 싶을 경우 .rstrip()을 추가로 해 주는 것이 좋다. 또한 입력과 출력 스트림은 별개이므로, 테스트케이스를 전부 입력받아서 저장한 뒤 전부 출력할 필요는 없다. 테스트케이스를 하나 받은 뒤 하나 출력해도 된다. 자세한 설명 및 다른 언어의 경우는 이 글에 설명되어 있다. 이 블로그 글에서 BOJ의 기타 여러 가지 팁을 볼 수 있다.

 

지금까지 쓰던 input 대신에 sys.stdin.readline 이라는 것을 쓰라네요!

코드를 보면서 이해해봅시다!

 

import sys
N = int(sys.stdin.readline())

for i in range(N):
    print(sum(map(int, sys.stdin.readline().split())))

 

첫째줄의 import sys는 sys라는 라이브러리를 불러오는 것입니다.

다음 줄에 있는 sys.stdin.readline()을 쓰기 위한 것인데요.

 

input과의 차이는 무엇일까요?

 

제가 예전에 이해한 바로는!!

 

코드에서 input()을 만나면 입력창을 열어주고 엔터키를 치기 전까지 한 줄을 입력 받습니다. 그리고 한 줄 입력 후 입력창이 닫힙니다.

다음 줄을 또 받아오고 싶으면 input() 함수를 또 호출해야합니다.

시간이 많이 걸리겠쬬?

 

그런데 sys.stdin 라는 명령어를 만나면, 시스템적인 어떠한 경로를 통해서 여러줄 입력되어 있는 것들을 한번에 통째로 입력받습니다. 좀 빨라지겠죠? 느낌상으로도??

 

 

 

밑에 사진을 예로 들면,

 

에서

 

5
1  1
12 34
5 500
40 60
1000 1000

를 통째로 한번에 슉! 가져온다는 겁니다.

 

그런데 sys.stdin만 쓰게 되면 string도, integer도 아닌, 마치 동봉된 편지 형식 느낌인 '_io.TextIOWrapper' 라는 형식으로 받아오기 때문에

 

sys.stdin을 실제 사용할 때에는,

 

1. sys.stdin.readline() 이나

 

2. for line in sys.stdin: 의 포문을 사용하여 이용하게 되죠.

 

 

그래서 두 번째 줄

N = int(sys.stdin.readline()) 에서, sys.stdin 뒤에 readline()을 추가해준겁니다.

 

readline()을 붙이게 되면 한 줄만 읽어오는거죠.

한 줄을 읽어왔으니 5를 읽어온거고, 커서(키보드 깜빡깜빡 거리는 커서라고 생각하세요.)는 두번째 줄 맨 앞으로 이동합니다.

 

5를 읽어와서 int로 변수 종류를 바꿔주고, 그 수만큼 for문을 돌립니다.

 

첫번째 for문만 따라가볼게요.

 

sys.stdin.readline() 까지하면, 그 다음 줄인 {1 1\n}이 읽혀들어옵니다.

여기서 \n은 이스케이프코드, 즉 개행코드입니다. 줄을 바꿔주는 코드이죠.

이때 split()을 씁니다. split()은 whitespace 즉, 띄어쓰기, \n 등 공란을 기준으로 전부잘라서 남은 것들만 list로 저장합니다.

즉, {1 1\n}이 ---> [1,1]의 리스트가 됩니다.

 

저는 map을 사용해서 리스트 내의 원소하나하나를 integer로 바꿔주었구요, 이후 sum을 이용해 두 원소의 합을 구했습니다.

그걸 그대로 print 해준거구요!!

 

 

 

설명이 조금 장황하네요.

그래도 잘 이해하고 넘어가셨으면 하는 문제입니다!!! 

'Tech > 백준 단계별 문제' 카테고리의 다른 글

백준 2742 - 기찍 N (파이썬)  (0) 2020.04.30
백준 2741 - N찍기 (파이썬)  (0) 2020.04.29
백준 8393 - 합 (파이썬)  (0) 2020.04.27
백준 10950 - A+B-3 (파이썬)  (0) 2020.04.27
백준 2739 - 구구단 (파이썬)  (0) 2020.04.27

관련글 더보기