Codeforces389D(SummerTrainingDay01-J)
D. Fox and Minimal path
Fox Ciel wants to write a task for a programming contest. The task is: "You are given a simple undirected graph with nvertexes. Each its edge has unit length. You should calculate the number of shortest paths between vertex 1 and vertex 2."
Same with some writers, she wants to make an example with some certain output: for example, her birthday or the number of her boyfriend. Can you help her to make a test case with answer equal exactly to k?
Input
The first line contains a single integer k (1 ≤ k ≤ 109).
Output
You should output a graph G with n vertexes (2 ≤ n ≤ 1000). There must be exactly k shortest paths between vertex 1 and vertex 2 of the graph.
The first line must contain an integer n. Then adjacency matrix G with n rows and n columns must follow. Each element of the matrix must be 'N' or 'Y'. If Gij is 'Y', then graph G has a edge connecting vertex i and vertex j. Consider the graph vertexes are numbered from 1 to n.
The graph must be undirected and simple: Gii = 'N' and Gij = Gji must hold. And there must be at least one path between vertex 1 and vertex 2. It's guaranteed that the answer exists. If there multiple correct answers, you can output any of them.
Examples
input
2
output
4
NNYY
NNYY
YYNN
YYNN
input
9
output
8
NNYYYNNN
NNNNNYYY
YNNNNYYY
YNNNNYYY
YNNNNYYY
NYYYYNNN
NYYYYNNN
NYYYYNNN
input
1
output
2
NY
YN
Note
In first example, there are 2 shortest paths: 1-3-2 and 1-4-2.
In second example, there are 9 shortest paths: 1-3-6-2, 1-3-7-2, 1-3-8-2, 1-4-6-2, 1-4-7-2, 1-4-8-2, 1-5-6-2, 1-5-7-2, 1-5-8-2.
题意:求正好有k条最短路的图的邻接矩阵。
思路:二进制思想构图。
1 //2017-10-15 2 #include <cstdio> 3 #include <cstring> 4 #include <iostream> 5 #include <algorithm> 6 7 using namespace std; 8 9 const int N = 1100; 10 bool a[N][N]; 11 12 int main() 13 { 14 long long k; 15 while(cin>>k){ 16 int n = 0; 17 while((1<<n) <= k) 18 n++; 19 if(n)n--; 20 int step = n*2+1; 21 int num = (1<<n); 22 memset(a, 0, sizeof(a)); 23 n = 3*n+3; 24 a[1][3] = 1; 25 for(int i = 4; i <= n; i++){ 26 if(i%3 == 0)a[i][i-1] = a[i][i-2] = 1; 27 else if((i-1)%3 == 0)a[i][i-1] = 1; 28 else if((i-2)%3 == 0)a[i][i-2] = 1; 29 } 30 a[n][2] = 1; 31 for(int i = n+1; i < n+step; i++) 32 a[i][i+1] = 1; 33 a[n+step-1][2] = 1; 34 int tmp = k - num, ptr = 1; 35 while(tmp){ 36 int fg = (1&tmp); 37 tmp>>=1; 38 if(fg)a[(ptr+1)/2*3][ptr+n] = 1; 39 ptr+=2; 40 } 41 if(k != num)n+=(step-1); 42 cout<<n<<endl; 43 for(int i = 1; i <= n; i++){ 44 for(int j = 1; j <= n; j++) 45 if(a[i][j] || a[j][i]) 46 cout<<'Y'; 47 else cout<<'N'; 48 cout<<endl; 49 } 50 } 51 52 return 0; 53 }