본문 바로가기
C++

[C++] - 시간초과가 발생하는 경우 해결 방법

by 개발 고양이 2023. 11. 29.

C++를 이용하여 백준 문제를 풀면서 시간초과가 발생하는 경우, 아래의 두 줄을 추가해주면 해결되기도 한다.

	ios::sync_with_stdio(false);
	cin.tie(null);

 

이 코드의 의미가 무엇인지 알아보자.

 

ios_base::sync_with_stdio(false)

간단히 말해, C와 C++의 동기화를 비활성화시키는 코드이다.

단, 이 구문을 쓰게 되면 C와의 동기화가 해제되어 버퍼가 분리되었기 때문에 C의 입출력 방식(scanf, printf, gets, puts, getchar, putchar 등)을 사용할 수 없게 된다.

그러므로 입출력을 할 때 cin, cout와 같은 C++의 입출력 방식만 사용해야 한다. 

 

 

cin.tie(null)

cout << "이름을 입력하세요 : ";
cin >> name;

c++에서는 기본적으로 cin과 cout이 묶여있다.

묶여있는 스트림들은 한 스트림이 다른 스트림에서 입출력 작업을 진행하기 전에 자동으로 버퍼를 비워줌을 보장한다. 그래서 cout을 통해서 "이름을 입력하세요 : "라는 문장이 출력된 후, 입력받는 값을 name에 저장하게 된다. 

이때 cin.tie(null) (cin.tie(0)이라고 입력해도 상관 없다.) 코드를 추가하면 cin과 cout 사이를 묶어주지 않아도 되기 때문에 시간을 절약할 수 있게 된다. cin과 cout의 묶음이 풀리면 "이름을 입력하세요 : "를 화면에 띄우기 전에 name을 입력받는 것처럼, 입출력의 순서를 보장받을 수 없다는 단점이 있다.

하지만 백준 문제와 같이 알고리즘 문제를 풀 때에는 보통 출력만 잘 시키면 되기 때문에 꽤나 유용한 코드라고 할 수 있다. 

 

endl 대신 "\n" 사용하기

위 방법으로도 시간 초과가 해결되지 않는다면, endl을 사용하지는 않았는지 점검해보자. 

1. cout << "Hello World!" << endl;
2. cout << "Hello World!" << "\n";

1번과 2번 코드의 출력 결과는 서로 같다. 하지만 1번 코드가 2번보다 시간이 더 오래 걸린다.

 endl은 개행문자(줄바꿈)를 출력하면서 출력 버퍼를 비우는 명령까지 수행하기 때문에, "\n"보다 시간이 더 소요된다.

따라서 알고리즘 문제를 풀 때에는 endl보다는 "\n"을 사용하는 것이 좋다.

 


위의 방법을 모두 적용했는데도 시간 초과가 난다면?

코드의 시간 복잡도를 더 줄이는 방법밖에 없다..

알고리즘을 잘 생각해보고, 조금 더 효율적인 코드로 다시 짜봐야 한다.