bool dfs(int count,int pos,int res)這是本題中DFS算法的狀態。三個要素 count (已經拼好的棍子個數),pos (現在遍歷的第幾根棍子),res (要湊成目標長度剩余的長度) 當然在輸入數據以後要進行一次排序,從大到小排好依次遍歷。 我們要定義一個全局的變量 goal 代表你要湊齊的目標長度,換句話說就是總長度的 1/4 。
goal = sum/4;標記的數組我們定義為used[21].值為 true 則標記過,即用過了。值為 false 則未用過。
//聲明,全局 bool used[21]; //初始化為false,main函數中 memset(used,false,sizeof(used));下面看DFS函數的代碼:
bool dfs(int count,int pos,int res) { if(count==3)//3根拼好就能保證都拼好 return true; for(int i=pos;i//1:如果標記過就跳過下面過程 //2:先標記好true //3:如果第i根棍子的長度和你剩余的所需要的棍子的長度一樣。那麼這根棍子就拼好了
//4:由//3可知,又拼好了一根,所以遞歸下一個棍子要拼的狀態,count+1。而pos初始化為0.從頭開始便利,res變為goal,即下一根棍子剩余的長度是全部所需長度。
//5:如果第i根棍子的長度小於目前所需的。那麼也把它加上 //6:下一個狀態。count不變,因為這根還沒拼好。pos = i+1,因為第i根已用。res-stick[i] 不言而喻了。 //7:前面如果滿足的話,就會返回true。而不執行這一句//7這句。如果能走到//7這句,那麼就是說前面的情況都不成功,也就是說這根棍子不能湊近去,所以要推翻加入這根棍子的方案
完整代碼:#include#include using namespace std; bool used[21]; int stick[21]; int t,goal; bool cmp(int a,int b) { return a>b; } bool dfs(int count,int pos,int res) { if(count==3)//3根拼好就能保證都拼好 return true; for(int i=pos;i >n; while(n--) { cin>>t; int sum=0; for(int i=0;i >stick[i]; sum+=stick[i]; } if(sum%4) { printf("no\n"); continue; } goal = sum/4; memset(used,false,sizeof(used)); sort(stick,stick+t,cmp); if(dfs(0,0,goal))//初始態 printf("yes\n"); else printf("no\n"); } return 0; }