문제
A를 길이 N인 양의 정수로 구성된 배열이라고 하자.(N>2) 정수 P, Q(0<=P<Q<N) 에 대해서 A의 부분평균 A(P, Q)를 다음과 같이 정의하자.
∑i=PQA[i]Q−P+1
예를 들어 주어진 배열 A의 길이가 3이고
A[0]=3, A[1]=1, A[2]=2
라고 하면 A의 가능한 모든 부분평균은 다음과 같다.
A(0,1) = (3+1)/2 = 2
A(0,2) = (3+1+2)/3=2
A(1,2) = (1+2)/2=1.5
위와 같은 경우, 모든 부분평균 중 최솟값은 A(1,2)=1.5이다. 그렇다면 주어진 조건을 만족하는 임의의 배열 A가 주어지면 A의 부분평균 중 최솟값을 가지는 것을 A(u,v) 라고 할 때, u를 출력하는 프로그램을 작성하라. (답이 여러 개일 경우 가장 작은 u의 값을 출력한다.)
입력
N A[0], A[1], ..., A[N-1]
2 ≤ N ≤ 1,000,000, 0 ≤ A[i] ≤ 7×108
출력
u
힌트
P+1<Q 라면 P<K<Q 인 정수 K가 존재하여
혹은
이다.
힌트를 통해 해결해야 하는 문제.
브루트포스로 풀면 조진다.
길이가 1인 경우는 평균이 불가능
길이가 2라면 K + 1 < Q가 불가능
길이가 3이라면 저 식을 만족을 못한다. 위의 식이든 아래 식이든 모순 발생.
길이가 4이상 일때 가능하게 되는데, 100이든 99든 4든 쪼개지다보면 제일 작은 평균 값을 갖는 범위인 2나 3까지 내려온다.
따라서 2나 3은 애초에 저 조건으로 구할수 없으니 그대로 구하면되고 저 4부터는 저 조건으로 구하면 되기때문에
2나 3 범위만 확인하면 된다.
3부터 확인해야 하는데 2범위 평균이 3범위보다 작을 것이고 인덱스를 먼저 차지하는 과정에서
틀리는 히든케이스가 있을 것이라고 판단한다.
#include<iostream>
#include<string>
#include<algorithm>
#include<queue>
#include<vector>
#include<cmath>
#include<stack>
#include<set>
#include<map>
using namespace std;
double arr[1000000];
int main() {
ios_base::sync_with_stdio(false);
cin.tie(NULL);
int N;
cin >> N;
for (int i = 0; i < N; i++)
cin >> arr[i];
double mina = 987654321;
int idx = 0;
for (int i = 2; i < N; i++)
{
double temp = (arr[i - 2] + arr[i - 1] + arr[i]) / 3;
if (mina > temp)
{
mina = temp;
idx = i - 2;
}
}
for (int i = 1; i < N; i++)
{
double temp = (arr[i - 1] + arr[i]) / 2;
if (mina > temp)
{
mina = temp;
idx = i - 1;
}
}
cout << idx << endl;
}
'Algorithm' 카테고리의 다른 글
[2017 홍익대학교 프로그래밍 경진대회] 14925번 목장 건설하기 (0) | 2021.01.20 |
---|---|
[2017 홍익대학교 프로그래밍 경진대회] 14923번 미로 탈출 (0) | 2021.01.17 |
[2017 홍익대학교 프로그래밍 경진대회] 14921번 용액 합성하기 (0) | 2021.01.15 |
[2018 홍익대학교 프로그래밍 경진대회] 16401번 과자 나눠주기 (0) | 2021.01.14 |
[2018 홍익대학교 프로그래밍 경진대회] 16400번 소수 화폐 (0) | 2021.01.12 |