日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

2018美团CodeM编程大赛 Round A Problem 2 下棋 【贪心】

發布時間:2023/11/29 编程问答 32 豆豆
生活随笔 收集整理的這篇文章主要介紹了 2018美团CodeM编程大赛 Round A Problem 2 下棋 【贪心】 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

應該一眼看出來是貪心題,然后想最優解是什么。正確的貪心策略是【原棋盤上每個位置的棋子】都往最近的左邊【目標棋盤上棋子】移動,如果左邊沒有棋子了那就閑置最后處理,如果目標棋盤在該位置上也有棋子,那就算距離為0(最近)。最后處理的話,棋盤上的局面應該是所有的棋子都得往右移,這樣的話怎么移都無所謂了,樸素的把放過去。

模擬的時候難度在于通過upper bound找到離該位置最近左的位置,所以復雜度是O(NlogN);如果樸素的遍歷數組找最近左需要N復雜度,整體n^2就過不了了。

?

?對于upper_bound來說,返回的是被查序列中第一個大于查找值的指針,也就是返回指向被查值>查找值的最小指針,lower_bound則是返回的是被查序列中第一個大于等于查找值的指針,也就是返回指向被查值>=查找值的最小指針。 【引用自 https://blog.csdn.net/u011008379/article/details/50725670 】

?

1 #include<iostream> 2 #include<algorithm> 3 #include<map> 4 #include<vector> 5 using namespace std; 6 7 int board[100005]; 8 vector<int> va; 9 map<int,int> m; 10 long long ans; 11 //貪心策略 12 //每個都向自己最近的左邊的棋子移動 13 int main(){ 14 int n; cin>>n; 15 for(int i=1;i<=n;i++) cin>>board[i]; 16 for(int i=1;i<=n;i++){ 17 int x; cin>>x; 18 if(x){//這個位置上有棋子 19 va.push_back(i); 20 m[i]=x; 21 } 22 } 23 24 for(int i=1;i<=n;i++){ 25 while(1){ 26 vector<int>::iterator index = upper_bound(va.begin(),va.end(),i);/* index指向第一個大于i的元素 */ 27 //如果沒有比i還大的,返回begin() 28 if(index==va.begin()) break;//目標盤左邊沒有棋子了 29 index--; 30 if( m[ *index ]>board[i] ) { 31 ans+=(i-(*index) )*board[i]; 32 m[*index]-=board[i]; 33 board[i]=0; 34 break; 35 } 36 if( m[ *index ]==board[i] ){ 37 ans+=(i-(*index))*board[i]; 38 va.erase(index); 39 board[i]=0; 40 break; 41 } 42 if( m[ *index]<board[i]){ 43 ans+=(i-(*index))*m[ *index]; 44 va.erase(index); 45 board[i]-=m[*index]; 46 } 47 } 48 } 49 50 for(int i=1;i<=n;i++){ 51 if(board[i]==0) continue; 52 while(1){ 53 if( m[ va[0] ]>board[i] ) { 54 ans+=(i+va[0]-2)*board[i]; 55 m[ va[0] ]-=board[i]; 56 break; 57 } 58 if( m[ va[0] ]== board[i] ){ 59 ans+=(i+va[0]-2)*board[i]; 60 va.erase(va.begin()); 61 break; 62 } 63 if( m[ va[0] ]<board[i]){ 64 ans+=(i+va[0]-2)*m[ va[0] ]; 65 va.erase(va.begin()); 66 board[i]-=m[ va[0] ]; 67 } 68 } 69 } 70 71 cout<<ans<<endl; 72 73 return 0; 74 }

沒有提交在美團的oj上,但自己編了幾個數據都過了。

轉載于:https://www.cnblogs.com/ZhenghangHu/p/9162910.html

總結

以上是生活随笔為你收集整理的2018美团CodeM编程大赛 Round A Problem 2 下棋 【贪心】的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。