灵犀互娱笔试第五题,出自HDU
http://acm.hdu.edu.cn/showproblem.php?pid=1466
假设平面上有n条直线,且不存在三条或以上直线共点的情况,求这n条直线可能存在多少种不同交点数.
例n=2,则可能的交点数量为0(平行)或者1(不平行)。
输入数据包含多个测试实例,每个测试实例占一行,每行包含一个正整数n(n<=20),n表示直线的数量.
Output
每个测试实例对应一行输出,从小到大列出所有相交方案,其中每个数为可能的交点数,每行的整数之间用一个空格隔开。
动态规划
状态表示 f[i][j]表示i条直线,j个交点是否存在。
集合划分 m条直线的交点数 = (m - r)条平行线与r条直线交叉的交点数 + r条直线本身交点数 = (m - r) * r + r条直线本身交点数
只要f[i][j] = 1,那f[i][(i - r) * r + j] = 1;
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38
| #include <iostream> #include <vector> using namespace std;
int main() { string line; vector<int> a; while (getline(cin, line)) { a.push_back(stoi(line)); } for (int i = 0; i < a.size(); i++) { int n = a[i]; vector<vector<int>> f(25, vector<int> (200)); f[0][0] = f[1][0] = 1; for (int i = 2; i <= n; i++) { f[i][0] = 1; for (int j = 0; j < i; j++) { for (int k = 0; k <= n * (n - 1) / 2; k++) { int b = i - j - 1; if (f[b][k] == 1) { f[i][(i - b) * b + k] = 1; } } } } for (int j = 0; j <= n * (n - 1) / 2; j++) { if (f[n][j] == 1) { cout << j << " "; } } cout << endl; } return 0; }
|