POJ 1228おじいちゃんの不動産

POJ 1228おじいちゃんの不動産

問題の意味:元々凸多角形の爪やロープ、ロープで区切らその後、爪が残っている爪が元の凸多角形を決定することができるかどうかを決定する、失っています。

変換:条件が満たさ:残りの釘は凸包構成することができ、そして各側面は、少なくとも3つの爪を有し、残りの爪少なくとも6、凸包の少なくとも3つの頂点。

アルゴリズム:; //データ範囲が1000であり、n ^ 2凸包構造は、各力の側面は、三点があるか否かを判断します

凸状のパッケージを感謝しました:

#include <iostreamの> 
する#include <cmath> 
の#include <アルゴリズム> 
の#include <cstdioを>
 使用して 名前空間STD; 

のconst  int型 MAXN = 1010 ; // これは、RTは、本明細書チェックポイントの数であり、
CONST  ダブル PI = ACOSは( - 1.0 );
 // 精度
ダブル EPS = 1E- 。8 ;
 // 避ける-0.00場合、EPSの最後の増加
 // 精度比較
INT SGN(ダブルX)
{ 
    IF(FABS(X)<= EPS)戻り 0 ;
     IF(X < 0リターン - 1。;
     リターン 1 ; 
} 

// 点パッケージ
構造体のポイント
{ 
    ダブルX、Y、
    ポイント(){} 
    // 割り当て 
    ポイント(ダブル _x、ダブル_y)
    { 
        X = _x; 
        Y = _y; 
    } 
    // ポイント減算 
    ポイント演算子 - (CONST点B&)のconst 
    { 
    戻り点(xb.x、Y- によって); 
    } 
    // 内積
    二重  演算子 *(CONSTポイントB&)のconst 
    { 
        戻り * X + Yをb.x によって; 
    } 
    // 外積
    ダブル 演算子 ^(CONST   ポイントB&)のconst 
    { 
        戻り副X * Y *をBX; 
    } 
}; 

// 包装ラインの
構造体のライン
{ 
    ポイントS、E、
    ライン(){} 
    線(点_s、ポイント_E)
    { 
        S = _s; 
        E = _E; 
    } 
// 平行と交差する出力一致判定交差点
 @直線が交差すると決意を重複なく、線分、演算子&(CONSTライン&B)のconst { 
    ポイントRES = BS;
     IF(SGN((ES)^(BE-BS))== 0 
    { 
        IF(SGN((ES) ^(eb.e))== 0 
        { 
            // 一致
            戻り点(00 ); 
        } 
        
            { 
               // 平行
                リターンポイント(00 ); 
            } 
    } 
    ダブル T =((ES)^(SBを。 S))/((ES) ^(BE-BS)); 
    res.x + =(のBEx-BSX)* T; 
    res.y + =(ベイ-BSY)* T;
     戻りRESを; 
    } 
}; 

// ベクトル外積
ダブルxmult(点P0、P1点、 P2点)
{ 
    リターン(P0-P1)^(P2- P1); 
} 

// 線分を線分が非厳密に交差し、trueに交差
 // ここでセグメント
BOOLのseg_seg(ラインL1、L2行)
{ 
    戻り SGN(xmult (l1.s、l2.s、l2.e)* xmult(l1.e、l2.s、l2.e))<= 0 && SGN(xmult(l2.s、l1.s、l1.e)* xmult (l2.e、l1.s、l1.e))<= 0 ; 
} 

// 両者間の距離
の二重DIST(点A、点B)
{ 
    戻り SQRT((AB&)*(AB& )); 
} 

// 極角ソーティング; 100ポイント極角ソートする
int型の POSを; // 極添字
点p [MAXN ];
 INT スタック[MAXN]、トップ;
 BOOL CMP(点A、点B)
{ 
    ダブル TMP = SGN((AP [POS])^(BP [POS])); // ソート反時計
    IF( == TMP 0リターン DIST(A、P [POS])< DIST(B、P [POS]);
     IF(TMP < 0リターン falseに戻り trueに; 
} 
ボイドグラハム(int型N)
{ 
    点P0。
    int型のk = 0 
    P0 = P [ 0 ]。
    int型 i = 1 ; iが<N; iが++)// 找到最左下边的点
    {
         場合(p0.y> P [I] || .Y(SGN(p0.yp [I] .Y))= = 0 && P0.X> P [I] .X)
        { 
            P0 = P [i]は、
            kは = I。
        } 
    } 
    スワップ(P [K]、P [ 0 ])。
    ソート(P + 1、P + N、CMP)。
    もし(nは==1 
    { 
        トップ = 2 
        スタック[ 0 ] = 0 返します
    } 
    であれば(N == 2 
    { 
        トップ = 2 
        スタック[ 0 ] = 0 
        スタック[ 1 ] = 1 返します
    } 
    スタックは[ 0 ] = 0 ;スタック[ 1 ] = 1 
    トップ = 2 以下のためにint型 I = 2、iは<N; iは++ 
    { 
        一方(TOP> 1つの && SGN((P [スタック[トップ1 ] - P [スタック[トップ2 ])^(P [I] -p [スタック[トップ2 ]))<= 0 
            トップ - 
        [トップスタック ++] = I; 
    } 
} 
 int型のn;
ブールチェック()
{ 
    場合(N < 6を返す  場合(トップ< 2を返す にとってint型 I = 0 ; iがトップ< 1 ; iが++ 
    { 
        int型 ANS = 0 INT J = 0 J ++; J <N であれば(P、xmult(P [J] [スタック[I]、P [スタック[I + 1 ]])== 0 
                ANS ++ 場合(ANS < 3 を返す 
    } 
    を返す 
} 
int型のmain()
{ 
    int型のT。
    CIN>> トン;
    一方、(t-- 
    { 

        CIN >> N。
        以下のためにint型 i = 0 ; iがn <I ++は
            CIN >> P [i]は.X >> Pを[I] .Y。
        グラハム(N)// N和トップ都是指点的个数
        場合(チェック())
            COUT << " YES " << ENDL。
        他の
            裁判所未満 << " NO " << てendl; 
    } 
}

 

おすすめ

転載: www.cnblogs.com/zwx7616/p/11237059.html