dp[i][j]=1表示用前i个数字可以凑成余数为j。
若dp[i-1][j]=1 ,则dp[i][(j+num[i])%k]=1;dp[i][((j-num[i]+k)%k+k)%k]=1
#include <iostream> #include <cstdio> #include <cstring> #include <algorithm> using namespace std; int num[10010]; int dp[10010][110]; int main() { int t; scanf("%d",&t); while(t--){ memset(dp,0,sizeof(dp)); int n,m; scanf("%d%d",&n,&m); for(int i=1;i<=n;i++){ scanf("%d",&num[i]); num[i]=abs(num[i]); } dp[1][num[1]%m]=1; for(int i=1;i<=n;i++){ for(int j=0;j<m;j++){ if(dp[i-1][j]){ dp[i][(j+num[i])%m]=1; dp[i][((j-num[i]+m)%m+m)%m]=1; } } } if((dp[n][0]==1)){ printf("Divisible\n"); } else{ printf("Not divisible\n"); } } return 0; }