1. 程式人生 > >湖南大學第十四屆ACM程式設計大賽 D Dandan's lunch

湖南大學第十四屆ACM程式設計大賽 D Dandan's lunch

連結:https://ac.nowcoder.com/acm/contest/338/D
來源:牛客網
時間限制:C/C++ 1秒,其他語言2秒
空間限制:C/C++ 65536K,其他語言131072K
64bit IO Format: %lld

題目描述

    As everyone knows, there are now n people participating in the competition. It was finally lunch time after 3 hours of the competition. Everyone brought a triangular bread. When they were going to eat bread, some people found that they solved more problems than others, but their bread was smaller than others. They thought it was very unfair. In this case, they will forcibly exchange bread with the other party (may be exchanged many times, someone can still exchange with others after being exchanged if the above conditions are satisfied, the other party can not refuse).
    The description of the bread is given by the coordinates of the three vertices of the triangle. The size of the bread is twice the size of the triangle area, ensuring that there are no two breads of the same size, and the number of problems each person makes is different.
    Dandan is also one of the contestants. Now he knows the number of problems solved by each person and the description of the bread they bring. Now he wants to know that after all the exchanges are over (That is, there can be no more exchanges between any two people), The size of the bread he can get.   

輸入描述:

The first line gives an integer n, which indicates the number of people who participated in the competition.
Lines 2~n+1, each line gives 7 integers separated by spaces such as:
num x1 y1 x2 y2 x3 y3
num represents the number of the ith personal problem solving. (x1, y1) (x2, y2) (x3, y3) represents the coordinates of the three points of the bread of the triangle with the i-th person. ensure that three points are not in the same line.
Notice that the second line (the first person) represents Dandan's information.
Data guarantee: 0<n<=1e5,0<=num<1e9, -1e8<x1, x2, x3, y1, y2, y3<1e8.

輸出描述:

Outputs an integer representing the size of the bread that DanDan eventually gets.

示例1

輸入

複製

1
100000000 0 0 10000 0 0 1000

輸出

複製

10000000

說明

There's only Dandan alone.

示例2

輸入

複製

4
3 0 0 1 0 0 1
1 0 0 2 0 0 2
2 0 0 3 0 0 3
4 0 0 4 0 0 4

輸出

複製

9

說明

Dandan solved three problems, ranking second. Ranking first can get the biggest bread, so he can get the second largest bread.

備註:

1e5=100000
1e8=100000000
1e9=1000000000

題目大意:

眾所周知,現在有N個人參加了比賽。比賽進行了3個小時後,終於到了吃午飯的時間。每個人都帶了一個三角麵包。當他們準備吃麵包時,一些人發現他們解決的問題比其他人多,但他們的麵包比其他人小。他們認為這很不公平。在這種情況下,他們會強行與對方交換麵包(可以多次交換,如果滿足上述條件,對方不能拒絕,交換後仍可以與他人交換)。
麵包的描述由三角形三個頂點的座標給出。麵包的大小是三角形區域的兩倍,確保沒有兩個相同大小的麵包,每個人製造的問題數量也不一樣。
丹丹也是參賽者之一。現在他知道每個人解決的問題的數量和他們帶來的麵包的描述。現在他想知道,在所有的交換都結束後(也就是說,任何兩個人之間都不能再交換),他能得到的麵包的大小。
第一行給出一個整數n,表示參加比賽的人數。
第2行~n+1,每行給出7個整數,用空格分隔,例如:
數字x1 y1 x2 y2 x3 y3
num表示第i次個人問題解決的次數。(x1,y1)(x2,y2)(x3,y3)表示三角形麵包的三個點與第i個人的座標。確保三個點不在同一條線上。
注意,第二行(第一個人)表示丹丹的資訊。
資料保證:0<n<1e5,0<num<1e9,-1e8<x1,x2,x3,y1,y2,y3<1e8。
輸出一個整數,表示丹丹最終得到的麵包大小。

分析:題目說的很詳細,那麼,做題最多的人一定會得到最大的麵包,做題第二多的人一定會得到第二大的麵包。。。。做題最少的人一定會得到最小的麵包,將每個人的做題數和麵包大小進行排序,輸出對應的麵包大小即可。關鍵在於如何求麵包的大小,題目提供了麵包的三個點座標。還說了麵包的大小是三角形區域的兩倍,我們就可以聯想到用三點求三角形面積後再擴大2倍就是麵包的大小。

設A(x1,y1),B(x2,y2),C(x3,y3)
由A-->B-->C-->A 按逆時針方向轉。(行列式書寫要求)
設三角形的面積為S
則S=(1/2)*(下面行列式)
|x1 y1 1|
|x2 y2 1|
|x3 y3 1|
S=(1/2)*(x1y2*1+x2y3*1+x3y1*1-x1y3*1-x2y1*1-x3y2*1)
即用三角形的三個頂點座標求其面積的公式為:
S=(1/2)*(x1y2+x2y3+x3y1-x1y3-x2y1-x3y2)

則2S=(x1y2+x2y3+x3y1-x1y3-x2y1-x3y2)

注意求面積的結果是絕對值的形式。

#include<iostream>
#include<algorithm>
#define ll long long
using namespace std;
ll area(ll x1,ll y1,ll x2,ll y2,ll x3,ll y3)//已知三點求三角形面積
{
    return (labs(x1*y2+x2*y3+x3*y1-x1*y3-x2*y1-x3*y2));//注意結果要取絕對值
}
 
int main()
{
    long long x,n[100005],x1,y1,x2,y2,x3,y3,s[100005],k;
    cin>>x;
     
    for(int i=1;i<=x;i++)
    {
        cin>>n[i]>>x1>>y1>>x2>>y2>>x3>>y3;//依次輸入每點做題數及三點座標
        s[i]=area(x1,y1,x2,y2,x3,y3);
    }
    k=n[1];
    sort(n+1,n+x+1);//對做題數進行排序
    sort(s+1,s+x+1);//對面包大小進行排序
    for(int i=1;i<=x;i++)//對於大資料容易超時,建議使用二分查詢。
    {
        if(n[i]==k)//如果查詢資料做題數相對應
        {
            cout<<s[i]<<endl;//輸出對應麵包大小
            break;
        }
    }
}