Problem Description
Given a set of sticks of various lengths, is it possible to join them end-to-end to form a square?
Input
The first line of input contains N, the number of test cases. Each test case begins with an integer 4 <= M <= 20, the number of sticks. M integers follow; each gives the length of a stick - an integer between 1 and 10,000.
Output
For each case, output a line containing "yes" if is is possible to form a square; otherwise output "no".
Sample Input
3 4 1 1 1 1 5 10 20 30 40 50 8 1 7 2 6 4 4 3 5
Sample Output
yes no yes一万点尴尬,越搜越晕//构造四条边 //如果加和不是四的倍数显然不能构成 //边的长度大于四分之一总和也不能构成 //构成一条边,继续递归搜索时,长度变成0,继续从第一个位置进行搜索 //直到bian == 4,立个flag,结束#include <iostream> #include <stdio.h> #include <string.h> #include <algorithm> #include <fstream> int in[22]; int vis[22]; int flag; int pd, num, sum; using namespace std; void sear(int bian, int line, int place) { if(bian == 4) { flag = 1; return; } if(line == pd) { sear(bian + 1, 0, 0); if(flag) return; } for(int i = place; i < num; i++) { if(!vis[i] && (line + in[i])<= pd) { vis[i] = 1; sear(bian, line + in[i], i + 1); //如果上面那种情况符合条件,不再继续判断 if(flag) return; vis[i] = 0; } } return; } int main() { //freopen("in.txt", "r", stdin); int n; scanf("%d", &n); while(n) { n--; sum = 0; scanf("%d", &num); for(int i = 0; i < num; i++) { scanf("%d", &in[i]); sum += in[i]; } if(sum % 4 != 0) printf("no\n"); else { pd = sum / 4; //printf("%d\n", pd); int i; for(i = 0; i < num; i++) { if(in[i] > pd) break; } if(i != num) { printf("no\n"); continue; } memset(vis, 0, sizeof(vis)); flag = 0; sear(0, 0, 0); if(flag) printf("yes\n"); else printf("no\n"); } } return 0; }