動態獲取某個元素的高度_codeforces 1443D,解法簡單,思維縝密的動態規劃問題...

bd12ee1201758738f2e1b3664bf0777e.png

大家好,歡迎來到codeforces專題。

今天選擇的問題是1443場次的D題,這題是全場倒數第三題,截止到現在一共通過了2800余人。這題的思路不算難,但是思考過程非常有趣,這也是這一期選擇它的原因。

鏈接:https://codeforces.com/contest/1443

a2acdcb965cbbbe00c86a949ce897cb7.png

廢話就先說到這里,下面我們就來看題吧。

題意

給定n個整數,對于這n個整數我們可以采取兩種操作。第一種操作是在數組左側選擇連續的k個整數減1,第二種操作是選擇右側的連續k個整數減1

比如假設數組是[3, 2, 2, 1, 4],比如我們選擇k=2,取最左側進行操作,那么我們會得到[2, 1, 2, 1, 4]。如果我們選擇k=3,再取右側進行操作,可以得到[2, 1, 1, 0, 3]。

現在我們想要知道,給定這樣的數組,我們能否通過這兩個操作將數組清空。如果可以輸出YES,否則的話輸出NO。

樣例

首先輸入一個整數t(

),表示測試數據組數。

對于每組測試數據,首先輸入一個整數n(

),表示數組當中元素的個數。之后輸入一行整數
)。可以保證,每一組測試數據的n之和不會超過30000.

bcc63a3de32b4c911d21cf39804c50e4.png

題解

由于我們對于k沒有限制,最多我們可以一次對數組內的n個元素全部減一。所以k不是限制我們的因素,最大的限制其實是在元素本身。

我們分析一下會發現,由于數組當中的元素大小不一,這其實是隱形的限制。舉個例子,比如[2, 8, 3]。由于我們只能從兩側開始選擇元素進行操作,所以由于2和3比較小,會導致我們沒有辦法把中間的8消除完。當然無法消除的原因可能有好幾種,但基本上都是由于元素的大小不一導致的。

首先我們對這個問題進行一個簡單的建模,題目當中沒有限制執行的次數,所以減一次和減很多次是一樣的。我們可以把可以合并的操作合并在一起,理解成執行一次可以減去任意的值。并且我們可以把操作反向理解,把數組當中的值看成是容器,這樣我們從數組當中減去值的操作,就可以等價理解成向容器當中輸入水流,這樣會容易理解一些。

我的第一想法很簡單,我們可以求出每個位置能夠從左側和右側分別獲得的最大數值。只要左右兩側能夠獲取的流量之和大于等于容器的容積,那么就說明我們可以獲取到足夠的流量灌滿所有的容器。

我很快就寫出了代碼,建了一個二維數組,dp[i][0]表示第i個元素從左側源頭能夠獲取的最大流量。dp[i][1]表示第i個元素可以從右側源頭獲取到的最大流量。由于我們需要保證每個容器存儲的體積不能超過容量,所以我們需要很容易得出遞推關系。

dp[i][0] = min(dp[i-1][0], a[i])

關系明確了很容易寫出代碼:

using namespace std;int a[30006], dp[30006][2];int main() {int t, n;scanf("%d", &t);rep(z, 0, t) {scanf("%d", &n);rep(i, 1, n+1) scanf("%d", &a[i]);MEM(dp, 0x3f);// 從左側遞推,獲取dp[i][0]rep(i, 1, n+1) {dp[i][0] = min(dp[i-1][0], a[i]);}// 從右側遞推,獲取dp[i][1]Rep(i, n, 0) {dp[i][1] = min(dp[i+1][1], a[i]);}bool flag = 1;rep(i, 1, n+1) {// 如果存在某個元素從左右兩側獲取的流量之和無法灌滿// 則返回NOif (dp[i][0] + dp[i][1] < a[i]) {flag = 0;break;}}puts(flag ? "YES" : "NO");}return 0;
}

但是很遺憾,這樣不能AC,因為dp的數組維護的其實是某個位置從左側和從右側能夠獲取的最大值,這是一個理想情況,很有可能這個理想情況是無法實現的。

舉個很簡單的反例:[2, 4, 2, 4, 2],這些元素左右兩邊能夠獲取到的最大流量值都是2,但是這里是有問題的。觀察一下會發現數組當中的兩個4是無法同時滿足的,無法滿足的原因是因為中間的2限制了通過的流量。雖然理論上從左往右和從右往左能夠通過的流量上限都是2,但是這個上限是無法同時取到的

這個問題用上述的方法是解決不了的,所以需要重新構思。這里我們深入分析會發現一個比較麻煩的點,在于每個點都有兩個源頭,我們無法確定流量分配。不過這個問題也很好解決,因為左右兩邊的流量是沒有區別的。所以我們可以以某一側為主,剩余不夠的流量再由另一側補充。

比如我們可以以左側為主,把左側能夠獲取的流量開啟到最大,不夠地再通過右側補充。如果右側的流量無法補充,那么就說明無解。

我們用dp[i][0]記錄i位置從左側獲取的流量,dp[i][1]記錄i位置從右側獲取的流量。

#include <iostream>
#include <cstdio>
#include <cstring>
#include <queue>
#include <vector>
#include <cmath>
#include <cstdlib>
#include <string>
#include <map>
#include <set>
#include <algorithm>
#include "time.h"
#include <functional>
#define rep(i,a,b) for (int i=a;i<b;i++)
#define Rep(i,a,b) for (int i=a;i>b;i--)
#define foreach(e,x) for (__typeof(x.begin()) e=x.begin();e!=x.end();e++)
#define mid ((l+r)>>1)
#define lson (k<<1)
#define rson (k<<1|1)
#define MEM(a,x) memset(a,x,sizeof a)
#define L ch[r][0]
#define R ch[r][1]
const int N=1000050;
const long long Mod=1000000007;using namespace std;int a[30006], dp[30006][2], min_need[30006][2], record[30006][2];int main() {int t, n;scanf("%d", &t);rep(z, 0, t) {scanf("%d", &n);rep(i, 1, n+1) scanf("%d", &a[i]);MEM(dp, 0x3f);dp[0][1] = 0;bool flag = 1;rep(i, 1, n+1) {# 如果右側需要的流量大于容器容積if (dp[i-1][1] > a[i]) {flag = 0;break;}# 左側能夠獲取的流量,因為i-1從右側獲取的流量也會經過i,所以需要減去dp[i][0] = min(dp[i-1][0], a[i] - dp[i-1][1]);# 需要從右側獲取的流量需要累加dp[i][1] = dp[i-1][1] + max(0, a[i] - dp[i][0] - dp[i-1][1]);}puts(flag ? "YES" : "NO");}return 0;
}

雖然這個是很簡單的動態規劃的思想,但是一些細節很容易忽略。比如說i-1位置的右側流量會流經i以及大于i每一個位置。所以每一個位置的右側流量是累加的,是越來越大的。只要能夠把握住這點,AC是不難的。

總體來說這題的難度不大,對于思維的要求不是很高,但是非常考驗思維的縝密性和邏輯性。非常適合用來進行思維鍛煉。

今天的文章就到這里,衷心祝愿大家每天都有所收獲。如果還喜歡今天的內容的話,請來一個三連支持吧~(點贊、關注、轉發

原文鏈接,求個關注

原創 | codeforces 1443D,解法簡單,思維縝密的動態規劃問題?mp.weixin.qq.com

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/533262.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/533262.shtml
英文地址,請注明出處:http://en.pswp.cn/news/533262.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

顯卡的優化以提高計算機性能作用,顯卡優化,教您如何設置NVIDIA(英偉達)顯卡玩游戲性能更高...

多人玩游戲可能都只是在游戲中設置畫質選項&#xff0c;比如反鋸齒等&#xff1b;而對顯卡驅動控制面板中的設置并不關注。其實在顯卡驅動面板中設置游戲文件&#xff0c;可以更好的控制和提高游戲畫質、性能。那如何設置NVIDIA顯卡玩游戲性能更高&#xff1f;下面&#xff0c;…

服務器選購seo優化規則,如何選擇有利于SEO優化的空間服務器

之前我們講過域名&#xff0c;講過程序&#xff0c;今天我們來講解空間&#xff0c;其實空間主要影響SEO只有兩個方面&#xff0c;一個是速度&#xff0c;一個是穩定性&#xff0c;如果你的空間穩定性不夠&#xff0c;經常打不開&#xff0c;百度蜘蛛經常抓取不了&#xff0c;就…

安裝npm_Npm安裝包的版本號是如何更新的?

點擊右上方紅色按鈕關注“小鄭搞碼事”&#xff0c;每天都能學到知識&#xff0c;搞懂一個問題&#xff01;大家好&#xff01;我是/小鄭搞碼事/的小鄭今天和大家分享一下關于NPM安裝包的版本號是如何更新的問題。版本號&#xff1f;先來看一張圖上圖就是2.29.1就是安裝包Momen…

css 向左白色箭頭,帶CSS的工具提示左側的箭頭

使用正確的CSS屬性在工具提示的右邊添加箭頭。您可以嘗試運行以下代碼以在左側添加帶有箭頭的工具提示示例html>.mytooltip .mytext {visibility: hidden;width: 140px;background-color: blue;color: #fff;z-index: 1;top: -5px;left: 110%;text-align: center;border-radi…

python有理數_Python中的as_integer_ratio()用于減少給定有理數的分數

在本教程中&#xff0c;我們將編寫一個程序&#xff0c;該程序返回兩個數字&#xff0c;它們的比率等于給定的float值。我們有一個稱為as_integer_ratio()的方法&#xff0c;可以幫助實現我們的目標。讓我們看一些例子。Input:1.5Output:3 / 2Input:5.3Output:5967269506265907…

js上拉加載ajax數據,原生ajax寫的上拉加載實例

上拉加載的思路1 上拉加載是要把屏幕拉到最底部的時候觸發ajax事件請求數據2.所有要獲取屏幕的高度 文檔的高度 和滾動的高度 下面的代碼是已經做好了兼容的可以直接拿來用Javascript:alert(document.body.clientWidth); //網頁可見區域寬(body)alert(document.body.clientHeig…

b站前端大佬_知乎大佬強烈熱推的5個自學網站,看了幾個月,月薪三千漲三萬...

原標題&#xff1a;知乎大佬強烈熱推的5個自學網站&#xff0c;看了幾個月&#xff0c;月薪三千漲三萬現在很多踏入了社會的小伙伴們經常會覺得為什么工作能力提升不上去&#xff0c;主要是因為很少利用業余的時間來學習一些跟自己工作有關的專業知識來充實自己&#xff0c;這其…

xp系統如何開啟共享服務器,xp系統怎么關閉共享服務 xp系統共享打印機如何設置...

XP系統雖然已經出來很久了&#xff0c;但是仍然還有很多用戶在使用&#xff0c;其實不管哪個系統只要電腦可以正常使用就行。很多XP用戶在開啟共享功能之后&#xff0c;想關閉但是又不知道如何設置&#xff0c;那么下面小編就為大家分享XP系統關閉共享服務的步驟教程&#xff0…

用udp協議通訊時怎樣得知目標機是否獲得了數據包?_和相親對象聊天,你屬于UDP還是CDP?...

有人說和相親對象聊天就像ping服務器每發一條消息就像發出一條Ping命令等待對方回復從而得到響應速度結果但是難受的是這個響應速度永遠無法做到秒級少點幾分鐘多則幾十分鐘甚至幾十個小時才有響應有時候真希望對方不要響應了就能判斷此處Ping不通從此斷了念想...你是否也像這位…

三星w系列vip服務器,高端人士候機專屬特權 三星W2017一張行走的VIP卡

原標題&#xff1a;高端人士候機專屬特權 三星W2017一張行走的VIP卡17年春運時間為1月13日至2月21日&#xff0c;如今春節假期已過&#xff0c;億萬人開始踏上了離鄉之路追尋夢想。每年春運都給交通帶來巨大壓力&#xff0c;今年為期40天的春運預計全國發送旅客或超29億人次。鐵…

阿酷快捷鍵怎么使用_必須收藏!Linux用戶必須知道的常用終端快捷鍵

點擊上方[全棧開發者社區]→右上角[...]→[設為星標?]簡介&#xff1a;以下是一些每個 Linux 用戶必須使用的鍵盤快捷鍵。使用命令行時&#xff0c;這些 Linux 快捷鍵將提升你的工作效率。你知道什么把專業用戶和普通用戶分開的嗎&#xff1f;掌握鍵盤快捷鍵。好的&#xff01…

checkbox ajax 不選中的值,php – 無法通過ajax傳遞checkbox的值

我有從數據庫收到的表&#xff1a;//$id $_SESSION[staff_id];$teamResult getQuarter($leader_id);$count1 0;if (mysqli_num_rows($teamResult) > 0){?>1st Quarterwhile($row mysqli_fetch_array($teamResult)){$staff_id $row[staff_id];$username $row[usern…

3dmax天光渲染設置_【扮家家云渲染效果圖】3dmax測試全局照明效果|干貨教程...

首先打開場景文件&#xff0c;首先按快捷鍵8&#xff0c;打開環境和效果控制面板。下面有一個全局照明這樣一個選項卡&#xff0c;有染色、級別、環境光三個參數。默認情況下染色為白色&#xff0c;級別為1&#xff0c;環境光為黑色。此時我們可以單擊渲染&#xff0c;查看一下…

手寫table用ajax遍歷,原生js把數據循遍歷到前端table

用前端框架去給表格賦值簡直不要太容易和簡單。但是原生js就會復雜一些了。特別是按鈕事件的那個(“ )和 (’)特別讓人腦瓜子疼。最近做了一個功能&#xff0c;里面用的就是原生js實現。寫在js里面的代碼&#xff1a;(用的ajax請求將文件保存到服務器&#xff0c;返回的數據遍歷…

dbv mysql_MariaDB與MySQL對比 --- 對分布式事務的支持

本文最初于2016年底發表在我的個人微信公眾號里面&#xff0c;現略有修訂后發布在這里。本文的技術信息針對的是mysql-5.7.x和mariadb-10.1.9。MariaDB和MySQL兩者對分布式事務的支持有所不同&#xff0c;總的來說MySQL的支持更好&#xff0c;是完備的和可靠的(盡管后來也陸續發…

centos7下載安裝mysql步驟_Linux-centos7安裝mysql步驟

Centos7.3 yum安裝MySQL5.7.25擴展&#xff1a;在CentOS中默認安裝有MariaDB&#xff0c;這個是MySQL的分支&#xff0c;但為了需要&#xff0c;還是要在系統中安裝MySQL&#xff0c;而且安裝完成之后可以直接覆蓋掉MariaDB。1 下載并安裝MySQL官方的 Yum Repository[rootlocal…

mysql 常用命令的使用_MySQL基本命令

基操操作命令創建數據庫CREATE DATABASE 數據庫名&#xff1b;指定要操作的數據庫USE 數據庫名&#xff1b;創建數據表CREATE TABLE 數據表名&#xff1b;查看數據表SHOW CREATE TABLE 數據表名&#xff1b;使用DESCRIBE語句查看數據表DESCRIBE 數據表名&#xff1b;為數據表重…

織夢數據庫支持mysql5.7_最新織夢DEDECMS5.7數據庫說明文檔

最新織夢DEDECMS5.7數據庫說明文檔&#xff1a;dede_arctype 欄目管理表ID int(10) 欄目編號(自動編號)reID int(10) 父欄目編號topID int(10)sortrank smallint(6) 排序編號typename varchar(30) 欄目名稱typedir varchar(100) 欄目目錄isdefault smallint(6) 欄目列表選項(1鏈…

mysql ddl dql_MySQL的DDL和DML及其DQL數據庫操作

數據庫的基本概念1. 數據庫的英文單詞&#xff1a; DataBase 簡稱 &#xff1a; DB2. 什么數據庫&#xff1f;* 用于存儲和管理數據的倉庫。3. 數據庫的特點&#xff1a;1. 持久化存儲數據的。其實數據庫就是一個文件系統2. 方便存儲和管理數據3. 使用了統一的方式操作數據庫 -…

python模糊圖像清晰化_視頻模糊圖像處理

隨著科學技術的不斷發展和進步以及人們的安防意識不斷加強&#xff0c;人們對于安防技術的要求越來越高。電子監控在許多領域中都得到了廣泛的應用&#xff0c;如交通監控、軍事偵查、公共場所安全防范等。清晰的圖像能夠準確地鎖定犯罪證據和犯罪嫌疑人&#xff0c;能夠清晰地…