Codeforces 849B

来源:互联网 发布:深圳程序员猝死 编辑:程序博客网 时间:2024/06/05 03:11


B. Tell Your World


time limit per test 1second

memory limit per test     256megabytes


Connect the countless points with lines, till we reach thefaraway yonder.

There aren points on a coordinate plane, the i-th of which being (i, yi).

Determine whether it's possible to draw two parallel andnon-overlapping lines, such that every point in the set lies on exactly one of them, and each of thempasses through at least one point in the set.

Input

The first line of input contains a positive integern (3 ≤ n ≤ 1 000) — the number ofpoints.

The second line containsn space-separated integers y1, y2, ..., yn ( - 109 ≤ yi ≤ 109) — the verticalcoordinates of each point.

Output

Output "Yes" (without quotes) if it's possible to fulfill therequirements, and "No" otherwise.

Youcan print each letter in any case (upper or lower).

Examples

Input

5
7 5 8 6 9

Output

Yes

Input

5
-1 -2 0 0 -5

Output

No

Input

5
5 4 3 2 1

Output

No

Input

5
1000000000 0 0 0 0

Output

Yes


Note

In the first example, there are five points:(1, 7),(2, 5),(3, 8),(4, 6) and (5, 9). It's possible to draw a line thatpasses through points 1, 3, 5, and another one that passes through points 2, 4 and is parallel to the first one.

In the second example, while it's possible to draw two linesthat cover all points, they cannot be made parallel.

In the third example, it's impossible to satisfy both requirements at the sametime.

 



【题意】


给出坐标为(i,y[i])的一系列点,问能否找到两条平行且不重合的直线,使得所有点都落在两条直线上,且每条直线上至少有一个点。


【思路】


把问题转化一下,我们先算出两条直线的斜率k(由于两条直线平行,所以斜率相等),然后去找到两条直线最左下角的点作为基准点,检验其他点跟基准点之间的斜率是否为k即可。


那么我们如何去算这个k呢,一个个去枚举第一个点去其他点之间的斜率复杂度很大,这里我们需要脑洞一下,我们先去分别枚举第一个点与第二个点、第三个点之间的斜率k1,k2,如果与真正的斜率不同,则第一个点与第二个点不在同一直线上,与第三个点也不在同一直线上,那么说明第二个点和第三个点一定在同一直线上,算出斜率k3,真正的斜率一定是这三个里的一个。然后再去对每个斜率检查一下是否满足题目要求即可。



#include <cstdio>#include <cstring>#include <algorithm>using namespace std;const int maxn = 1005;int n;int y[maxn];bool solve(double k){    int flag=0;    int point=-1;                           //第一个点和第point个点是两个基准点    for(int i=2;i<=n;i++)     {        if(y[i]-y[1]==k*(i-1)) continue;        flag=1;                              //有两条不同的直线        if(point<0) point=i;        else if(y[i]-y[point]!=k*(i-point))  //超过了两条直线        {            flag=0;            break;        }    }    if(flag) return true;    return false;}int main(){    while(~scanf("%d",&n))    {        for(int i=1;i<=n;i++)        {            scanf("%d",&y[i]);        }        double k1=1.0*(y[2]-y[1]);        double k2=0.5*(y[3]-y[1]);        double k3=1.0*(y[3]-y[2]);        if(solve(k1)||solve(k2)||solve(k3)) puts("Yes");        else puts("No");    }    return 0;}



原创粉丝点击