- 題目描述:
-
一個整數數組,長度爲n,將其分爲m份,使各份的和相等,求m的最大值
比如{3,2,4,3,6} 可以分成{3,2,4,3,6} m=1;
{3,6}{2,4,3} m=2
{3,3}{2,4}{6} m=3 所以m的最大值爲3。
- 輸入:
-
存在多組數據,每組數據一定行爲一個正整數n(n<=64),第二行爲n個數字。當n爲0時,測試結束。
- 輸出:
-
輸出最大值m。
- 樣例輸入:
-
9 5 2 1 5 2 1 5 2 1 4 1 2 3 4 0
- 樣例輸出:
-
4 2
-
//////////////////////////////////////////////////////////////////////////
-
最近懶癌又發作了
-
數字分組要從數組最大的元素開始分配,因爲一般來說,最大元素配成一組選擇的範圍要小於至多等於稍小的元素,所以代碼如下:
-
-
if(msum[m]==mv)//當前分組剛好符合要求,進行下一組分配
if(rev(v,i+1,msum,m,mv))//表面當前元素能被接納,所以可以進行下一個元素分組
msum[m]+=v[i]; -
#include<iostream> #include<string.h> using namespace std; bool ga; bool used[65]; int n; bool rev(int*v,int vlen,int*msum,int m,int mv)//msum是用來記錄當前分組的和是多少,m是當前第幾個分組(從大到小),mv表示每個分組和的最大值 { if(m==0)//已經將所有元素分配好了 { ga=true; return true; } return rev(v,0,msum,m-1,mv);//當前分組剛好符合要求,進行下一個分組 int i; for(i=vlen;i<n;i++) { if(used[i]||msum[m]+v[i]>mv)//將沒分配過的元素分配到當前組溢出,表明此分配不適合,下一個接着分配 continue ; used[i]=true; { ga=true; return true; } msum[m]-=v[i]; used[i]=false; //if(msum[m]-v[i]==0)//最大的已經試過了 //break; if(msum[m]==0) break; while(i<n-1&&v[i]==v[i+1]) i++; } return false; } int main() { while(cin>>n&&n!=0) { int v[65]; int j,k,i,temp,sum; for(j=0;j<n;j++)//這裏的排序感覺效率不佳,可以用sort函數 { if(j==0) { cin>>v[0]; sum=v[0]; } else { cin>>v[j]; sum+=v[j]; for(k=0;k<j;k++) if(v[j]>v[k]) break; temp=v[j]; for(i=j;i>k;i--) v[i]=v[i-1]; v[k]=temp; } } int msum[65]={0}; ga=false; for(j=(sum/v[n-1])<n?(sum/v[n-1]):n;j>1;j--) if(sum%j==0) { memset(used,0,sizeof(used)); memset(msum,0,sizeof(msum)); rev(v,0,msum,j,sum/j); if(ga) { cout<<j<<endl; break; } } if(!ga) cout<<1<<endl; } return 0; } /************************************************************** Problem: 1251 User: 午夜小白龍 Language: C++ Result: Accepted Time:10 ms Memory:1520 kb ****************************************************************/