Hdu3231 step5.2.7 Box Relations(拓撲排序)

Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)

Total Submission(s): 876    Accepted Submission(s): 313

Special Judge

 

Problem Description

There are n boxes C1, C2, ..., Cn in 3Dspace. The edges of the boxes are parallel to the x, y or z-axis. We providesome relations of the boxes, and your task is to construct a set of boxessatisfying all these relations.

 

There are four kinds of relations (1 <=i,j <= n, i is different from j):

I i j: The intersection volume of Ci and Cjis positive.

 

X i j: The intersection volume is zero, andany point inside Ci has smaller x-coordinate than any point inside Cj.

 

Y i j: The intersection volume is zero, andany point inside Ci has smaller y-coordinate than any point inside Cj.

 

Z i j: The intersection volume is zero, andany point inside Ci has smaller z-coordinate than any point inside Cj.

.

 

 

Input

There will be at most 30 test cases. Eachcase begins with a line containing two integers n (1 <= n <= 1,000) and R(0 <= R <= 100,000), the number of boxes and the number of relations.Each of the following R lines describes a relation, written in the formatabove. The last test case is followed by n=R=0, which should not be processed.

 

 

Output

For each test case, print the case numberand either the word POSSIBLE or IMPOSSIBLE. If it's possible to construct theset of boxes, the i-th line of the following n lines contains six integers x1,y1, z1, x2, y2, z2, that means the i-th box is the set of points (x,y,z)satisfying x1 <= x <= x2, y1 <= y <= y2, z1 <= z <= z2. Theabsolute values of x1, y1, z1, x2, y2, z2 should not exceed 1,000,000.

 

Print a blank line after the output of eachtest case.

 

 

Sample Input

3 2

I 1 2

X 2 3

3 3

Z 1 2

Z 2 3

Z 3 1

1 0

0 0

 

 

Sample Output

Case 1: POSSIBLE

0 0 0 2 2 2

1 1 1 3 3 3

8 8 8 9 9 9

 

Case 2: IMPOSSIBLE

 

Case 3: POSSIBLE

0 0 0 1 1 1

 

 

Source

2009 Asia Wuhan Regional Contest Hosted byWuhan University

 

題解:

這道題是一道很好的題,在3D的空間中,長方體i在每一維看成是兩個點,如在x軸上,長方體i的兩個點是i和i+n(i表示左邊的點,i+n表示右邊的點,還未知道在x軸上的位置)。這道題給出了偏序關係,這個關係是小於關係。

1.I,兩個長方體x、y相交,在每個軸上都有x < y+n, y < x+n;

2.X,兩個長方體在X軸上,長方體x的兩個頂點都小於長方體的最左的頂點,即x+n < y;

3.Y,在y軸上有x+n<y;

4.Z,在Z軸上有x+n <y;

根據現有的偏序關係,用inx[],iny[],inz[]表示在特定軸上某個點的入度,即在現有條件下,某點比多少點大。而用vector vx[],vy[],vz[],記錄在特定軸上某點的出度的值,即在現有條件下比哪些點小,根據上面的偏序條件記錄後,進行拓撲排序,最後能將某軸上1到2*n個頂點拓撲完的,說明在該軸上,滿足條件。

 

源代碼:

#include <iostream>

#include <vector>

#include <stdio.h>

#include <string>

#include <queue>

#define MAX 2050

 

using namespace std;

int inx[MAX],iny[MAX],inz[MAX];

vector<int> vx[MAX],vy[MAX],vz[MAX];

int ansx[MAX],ansy[MAX],ansz[MAX];

int n,m;

 

void init()

{

   memset(inx,0,sizeof(inx));

   memset(iny,0,sizeof(iny));

   memset(inz,0,sizeof(inz));

 

   for(int i = 1;i <= 2*n;i++)

   {

     vx[i].clear();

     vy[i].clear();

     vz[i].clear();

   }

 

   for(int i = 1;i <= n;i++)

   {

     vx[i].push_back(i+n);

     inx[i+n]++;

     vy[i].push_back(i+n);

     iny[i+n]++;

     vz[i].push_back(i+n);

     inz[i+n]++;

   }

}

 

bool topologicalsort(int*in,vector<int> v[],int *ans)

{

   intnum = 0;

   queue<int>q;

 

   for(int i = 1;i <= 2*n;i++)

   {

     if(!in[i])

        q.push(i);

   }

 

   while(!q.empty())

   {

     intx = q.front();

     q.pop();

     ans[x] = num++;

 

     for(int i = 0;i < v[x].size();i++)

     {

        intf = v[x][i];

        in[f]--;

        if(!in[f])

          q.push(f);

     }

   }

 

   if(num== 2*n)

     returntrue;

   else

     returnfalse;

}

int main()

{

   intcount = 0;

   charc[5];

   intx,y;

   while(scanf("%d%d",&n,&m) != EOF &&n + m)

   {

     init();

     for(int k = 0;k < m;k++)

     {

        scanf("%s%d%d",c,&x,&y);

        if(c[0]== 'I')

        {

          vx[x].push_back(y+n);

          inx[y+n]++;

          vx[y].push_back(x+n);

          inx[x+n]++;

 

          vy[x].push_back(y+n);

          iny[y+n]++;

          vy[y].push_back(x+n);

          iny[x+n]++;

 

          vz[x].push_back(y+n);

          inz[y+n]++;

          vz[y].push_back(x+n);

          inz[x+n]++;

        }

 

        elseif(c[0] == 'X')

        {

          vx[x+n].push_back(y);

          inx[y]++;

        }

        elseif(c[0] == 'Y')

        {

          vy[x+n].push_back(y);

          iny[y]++;

        }

        elseif(c[0] == 'Z')

        {

          vz[x+n].push_back(y);

          inz[y]++;

        }

     }

     intflag = 1;

     if(!topologicalsort(inx,vx,ansx)){flag = 0;}

     if(!topologicalsort(iny,vy,ansy)){flag = 0;}

     if(!topologicalsort(inz,vz,ansz)){flag = 0;}

 

     count++;

     if(flag)

     {

        cout << "Case " << count <<": POSSIBLE" <<endl;

        for(int i = 1;i <= n;i++)

          cout<< ansx[i]<<" " <<ansy[i]<< " "  <<ansz[i] << " "

             << ansx[i+n]<<" "<<ansy[i+n]<<" " << ansz[i+n] <<endl;

        cout << endl;

     }

     else

     {

       

        cout << "Case "<<count <<": IMPOSSIBLE"<<endl<<endl;

     }

    

   }

   return0;

}

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章