洛谷P4093 [HEOI2016/TJOI2016]序列

来源:https://www.cnblogs.com/zwfymqz/archive/2018/02/10/8439823.html
-Advertisement-
Play Games

題目描述 佳媛姐姐過生日的時候,她的小伙伴從某寶上買了一個有趣的玩具送給他。玩具上有一個數列,數列中某些項的值可能會變化,但同一個時刻最多只有一個值發生變化。現在佳媛姐姐已經研究出了所有變化的可能性,她想請教你,能否選出一個子序列,使得在任意一種變化中,這個子序列都是不降的?請你告訴她這個子序列的最 ...


題目描述

佳媛姐姐過生日的時候,她的小伙伴從某寶上買了一個有趣的玩具送給他。玩具上有一個數列,數列中某些項的值可能會變化,但同一個時刻最多只有一個值發生變化。現在佳媛姐姐已經研究出了所有變化的可能性,她想請教你,能否選出一個子序列,使得在任意一種變化中,這個子序列都是不降的?請你告訴她這個子序列的最長長度即可 。

註意:每種變化最多只有一個值發生變化。在樣例輸入1中,所有的變化是:

1 2 3 
2 2 3 
1 3 3 
1 1 3
1 2 4 

選擇子序列為原序列,即在任意一種變化中均為不降子序列在樣例輸入2中,所有的變化是:

3 3 3
3 2 3

選擇子序列為第一個元素和第三個元素,或者第二個元素和第三個元素,均可滿足要

輸入輸出格式

輸入格式:

 

輸入的第一行有兩個正整數n, m,分別表示序列的長度和變化的個數。接下來一行有n個數,表示這個數列原始的狀態。接下來m行,每行有2個數x, y,表示數列的第x項可以變化成y這個值。1 <= x <= n。

 

輸出格式:

 

輸出一個整數,表示對應的答案

 

輸入輸出樣例

輸入樣例#1: 複製
3 4 
1 2 3 
1 2 
2 3 
2 1 
3 4
輸出樣例#1: 複製
3

說明

對於20%數據所有數字均為正整數,且小於等於300

對於50%數據所有數字均為正整數,且小於等於3,000

對於100%數據所有數字均為正整數,且小於等於100,000

 

這道題是DP應該不難看出來。

$dp[i]$表示選擇$i$以後所能形成的滿足條件的子序列的最大值

轉移的時候枚舉前面的點$(j)$。

設$MX[i]$表示$i$號位置能變成的最大值,$MI[i]$表示$i$號位置能變成的最小值,$a$為原序列

這樣轉移的時候會有兩個限制條件

$a[i]>=MX[j]$ && $MI[i]>=a[j]$

這很明顯是個二維偏序問題嘛,用CDQ樹套樹什麼的都可以搞。

樹套樹的話,將$a$抽象為$x$軸,將$MX$抽象為$y$軸

轉移的時候我們實際是在左下角為$(0,0)$,右上角為$MI[i],a[i]$的矩陣中查最大值

每次轉移對答案的貢獻的話實際上只是改變了$a[i],mx[i]$的值

然後就能很自然的想到樹套樹了,線段樹套線段樹或者樹狀數組套線段樹都可以搞

 

後者常數小一些

線段樹的數組一定要開的足夠大!!!!

 

 

#include<cstdio>
#include<cmath>
#include<algorithm>
using namespace std;
const int MAXN=6*1e6+10;
const int MAXNN=1e5+10;
const int INF=1e8+10;
inline int read()
{
    char c=getchar();int x=0,f=1;
    while(c<'0'||c>'9'){if(c=='-')f=-1;c=getchar();}
    while(c>='0'&&c<='9'){x=x*10+c-'0';c=getchar();}
    return x*f;
}
int root[MAXN],N,M,MX[MAXNN],MI[MAXNN],a[MAXNN];
struct S
{
    struct node
    {
        int ls,rs,mx;
    }T[MAXN];
    int tot;
    int query(int now,int ll,int rr,int pos)
    {
        if(ll==rr) 
            return T[now].mx;
        int mid=ll+rr>>1;
        if(pos<=mid) 
            return query(T[now].ls,ll,mid,pos);
        else 
            return max( T[T[now].ls].mx , query(T[now].rs,mid+1,rr,pos));    
    }
    void change(int &now,int ll,int rr,int pos,int val)
    {
        if(!now) now=++tot;
        T[now].mx=max(T[now].mx,val);
        if(ll==rr) return ;
        int mid=ll+rr>>1;
        if(pos<=mid) change(T[now].ls,ll,mid,pos,val);
        else          change(T[now].rs,mid+1,rr,pos,val);
    }
}tree;
struct B
{ 
    int N;
    int Tree[MAXNN];
    int lowbit(int p) {return p&(-p);}
    int Query(int k,int val)
    {
        int ans=0;
        while(k) 
        {
            ans=max(ans,tree.query(root[k],1,N,val));
            k-=lowbit(k);
        }
        return ans;
    }
    void Change(int k,int pos,int val)
    {
        while(k<=N)
        {
            tree.change(root[k],1,N,pos,val);
            k+=lowbit(k);
        }
    }
}BIT;
int main()
{
    //freopen("heoi2016_seq.in","r",stdin);
    //freopen("heoi2016_seq.out","w",stdout);
    N=read();M=read();
    for(int i=1;i<=N;i++) MX[i]=MI[i]=a[i]=read();
    for(int i=1;i<=M;i++)
    {
        int x=read(),y=read();
        MX[x]=max(MX[x],y);BIT.N=max(BIT.N,MX[x]);
        MI[x]=min(MI[x],y);
    }
    int ans=0;
    for(int i=1;i<=N;i++)
    {
        int now=BIT.Query(MI[i],a[i])+1;
        BIT.Change(a[i],MX[i],now);
        ans=max(ans,now);
    }
    printf("%d",ans);
    return 0;
}

 


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 明明一天都想著一會兒就更新,可是總是忘了,今天公司的項目上線倒是有點忙 這個月不是很順啊, 狗被金毛把腿咬了兩個洞,花錢不說,還不能洗澡,看著也怪心疼的, 摩托車忘了開U鎖就起步,導致鏈條蓋碎了, 公司加班太多缺少睡眠又莫名其妙的撞了頭,起了一個大包,裡外頭疼了好幾天, 沒有14薪了,只有13薪 看 ...
  • 接下來的幾篇博客,想記錄一下通過學習坦克大戰項目來循序漸進的學習Java基礎。主要是為了鞏固基礎知識,當然學習編程重要的還是多敲,問題通常是在敲代碼的過程中發現的,積累也是在敲代碼中尋求的經驗。這個坦克大戰項目是利用Java圖形界面來做的,比較簡陋。但是,在不斷的往裡面加功能的時候,可以學到很多知識 ...
  • 今天我給大家介紹的是python中的Number變數,與c++,java有些不同,下麵讓來為大家介紹: 在python中是不用聲明變數類型的,不過在使用變數前需要對其賦值,沒有值得變數是沒有意義的,編譯器也不會通過 一 : 整型 int: int 在python中的用法與c++大致是一樣的: a=1 ...
  • 上面測試,用了Junit 下邊枚舉 枚舉是什麼? 相當於 有點像單例模式,只造出一個對象供外界使用;這個枚舉一下造出好多個供使用,造出的對象不能改變 枚舉出來的ABCDE都是可以用類名.直接調用的對象,對象可以賦值,和調用其成員方法 ...
  • Java中成員訪問許可權 Java中的訪問許可權控制符有四個:作用域lxx__當前類____同一package___子孫類____其他package publiclxx___√lxx__lxx___√lxx__lxx__√lxx__lxx___√ protected___√lxx__lxx___√___ ...
  • ssh服務端 ssh客戶端 socket文件傳輸並校驗 服務端 socket文件傳輸並校驗 客戶端 ...
  • IOCP全稱IOCP全稱I/O Completion Port,中文譯為I/O完成埠。IOCP是一個非同步I/O的Windows I/O模型,它可以自動處理I/O操作,併在I/O操作完成後將完成通知發送給用戶。 ...
  • 資料庫準備—創建db_login資料庫 t_user表 1、創建web工程 2、創建用戶model user.java 3、創建util包 Dbutil.java 4、創建dao包 UserDao.java 5、創建servlet包 loginServlet 6、用戶登錄界面 login.jsp 跳 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...