CodeForces-1040B Shashlik Cooking(貪心)
阿新 • • 發佈:2018-12-16
題目大意:
n個節點,選擇一個節點的時候翻轉這個節點與兩側k個節點(夠的話),求最少幾次全部翻到反面。
ps:同一個節點翻兩次會翻回正面。
思路:
貪心,儘量多的選能翻翻2k+1個節點的節點,即在中間儘量多的劃分長度為2k+1的區間。為使中間節點數恰好為(2k+1)的整數倍,兩側特殊考慮。
在邊上最少翻k+1塊,最多2k+1,故兩邊留的總節點數d要滿足 2k+1d4k+2
當2k+2d3k+2時,一側取k+1的最小情況,一側根據剩餘節點選擇;
當3k+2d4k+2時,一側去2k+1的最大情況,一側根據剩餘節點選擇。
若找不出這個範圍內的d,直接輸出中點即可
#include<bits/stdc++.h> using namespace std; vector<int> ans; int main() { int n,k; scanf("%d%d",&n,&k); int d = n%(2*k+1); int t = n/(2*k+1); while(d<=n){ d+=2*k+1; if(d>=2*k+2&&d<=4*k+2) break; } if(d>=2*k+2&&d<=4*k+2&&d<=n){ ans.clear(); if(d<=3*k+2){ int l = d - 2 * k - 1; while(l<=n){ ans.push_back(l); l += 2 * k + 1; } } else{ int l = d - 3 * k - 1; while(l<=n){ ans.push_back(l); l += 2 * k + 1; } } printf("%d\n",ans.size()); for(int i=0;i<ans.size();i++) printf("%d ",ans[i]); printf("\n"); } else{ printf("1\n%d\n",(n+1)/2); } }