题目链接:戳我

对于一个排序二叉树来讲,它的中序遍历对应的序列是可以确定的.

我们知道如果求一个访问频率最低的(也就是没有修改),直接就区间DP即可.\(dp[i][j]=min(dp[i][j],dp[i][k]+dp[k+1][j]+sum[j]-sum[i-1])\)(其中sum表示访问频率的前缀和)

但是现在带上了修改qwq,所以我们肯定要多出来一个键值相关的维度.

键值很大,但是它的具体大小没什么意义,我们只需要知道他们的相对大小就行了,所以先离散化一下.我们可以凭借一个区间的最小的键值,来确定该区间表示的子树的根.

所以现在令\(f[i][j][k]\)表示在[i,j]区间中,最小的键值为k的答案.

那么有转移方程:

\(f[i][j][k]=min(f[i][p-1][k]+f[p+1][j][k]+sum[j]-sum[i-1]+K)\)(表示把p改为k)

\(f[i][j][k]=min(f[i][p-1][t[p].key]+f[p+1][j][t[p].key]+sum[j]-sum[i-1])\)(表示不对p进行修改)

#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cmath>
#define MAXN 75
using namespace std;
int n,K,tot,ans;
int sum[MAXN],pre[MAXN],f[MAXN][MAXN][MAXN];
struct Node{int key,s,id;}node[MAXN];
inline bool cmp(struct Node x,struct Node y){return x.id<y.id;}
int main()
{
#ifndef ONLINE_JUDGE
freopen("ce.in","r",stdin);
#endif
scanf("%d%d",&n,&K);
for(int i=1;i<=n;i++) scanf("%d",&node[i].id);
for(int i=1;i<=n;i++) scanf("%d",&node[i].key),pre[++tot]=node[i].key;
for(int i=1;i<=n;i++) scanf("%d",&node[i].s);
sort(&node[1],&node[n+1],cmp);
sort(&pre[1],&pre[tot+1]);
tot=unique(&pre[1],&pre[n+1])-pre-1;
for(int i=1;i<=n;i++) node[i].key=lower_bound(&pre[1],&pre[tot+1],node[i].key)-pre;
memset(f,0x3f,sizeof(f));
for(int i=1;i<=n+1;i++)
for(int k=1;k<=n;k++)
f[i][i-1][k]=0;
for(int i=1;i<=n;i++)
for(int k=1;k<=n;k++)
{
f[i][i][k]=node[i].s;
if(node[i].key<k) f[i][i][k]+=K;
}
for(int i=1;i<=n;i++) sum[i]=sum[i-1]+node[i].s;
// for(int i=1;i<=n;i++) printf("sum[%d]=%d\n",i,sum[i]); puts("");
for(int k=n;k>=1;k--)
{
for(int len=1;len<=n;len++)
{
for(int i=1,j=i+len-1;i<=n&&j<=n;i++,j++)
{
for(int p=i;p<=j;p++)
{
int cur=node[p].key;
f[i][j][k]=min(f[i][j][k],f[i][p-1][k]+f[p+1][j][k]+sum[j]-sum[i-1]+K);
if(cur>=k)
f[i][j][k]=min(f[i][j][k],f[i][p-1][cur]+f[p+1][j][cur]+sum[j]-sum[i-1]);
}
}
}
}
printf("%d\n",f[1][n][1]);
return 0;
}

NOI2013 二叉查找树的更多相关文章

  1. 数据结构:二叉查找树(C语言实现)

    数据结构:二叉查找树(C语言实现) ►写在前面 关于二叉树的基础知识,请看我的一篇博客:二叉树的链式存储 说明: 二叉排序树或者是一棵空树,或者是具有下列性质的二叉树: 1.若其左子树不空,则左子树上 ...

  2. 数据结构笔记--二叉查找树概述以及java代码实现

    一些概念: 二叉查找树的重要性质:对于树中的每一个节点X,它的左子树任一节点的值均小于X,右子树上任意节点的值均大于X. 二叉查找树是java的TreeSet和TreeMap类实现的基础. 由于树的递 ...

  3. codevs 1285 二叉查找树STL基本用法

    C++STL库的set就是一个二叉查找树,并且支持结构体. 在写结构体式的二叉查找树时,需要在结构体里面定义操作符 < ,因为需要比较. set经常会用到迭代器,这里说明一下迭代器:可以类似的把 ...

  4. 平衡二叉查找树(AVL)的理解与实现

    AVL树的介绍 平衡二叉树,又称AVL(Adelson-Velskii和Landis)树,是带有平衡条件的二叉查找树.这个平衡条件必须要容易保持,而且它必须保证树的深度是 O(log N).一棵AVL ...

  5. 二叉查找树 C++实现(含完整代码)

    一般二叉树的查找是通过遍历整棵二叉树实现,效率较低.二叉查找树是一种特殊的二叉树,可以提高查找的效率.二叉查找树又称为二叉排序树或二叉搜索树. 二叉查找树的定义 二叉排序树(Binary Search ...

  6. 数据结构——二叉查找树、AVL树

    二叉查找树:由于二叉查找树建树的过程即为插入的过程,所以其中序遍历一定为升序排列! 插入:直接插入,插入后一定为根节点 查找:直接查找 删除:叶子节点直接删除,有一个孩子的节点删除后将孩子节点接入到父 ...

  7. Java for LintCode 验证二叉查找树

    给定一个二叉树,判断它是否是合法的二叉查找树(BST) 一棵BST定义为: 节点的左子树中的值要严格小于该节点的值.    节点的右子树中的值要严格大于该节点的值.    左右子树也必须是二叉查找树. ...

  8. 数据结构和算法 – 9.二叉树和二叉查找树

      9.1.树的定义   9.2.二叉树 人们把每个节点最多拥有不超过两个子节点的树定义为二叉树.由于限制子节点的数量为 2,人们可以为插入数据.删除数据.以及在二叉树中查找数据编写有效的程序了. 在 ...

  9. 二叉树-二叉查找树-AVL树-遍历

    一.二叉树 定义:每个节点都不能有多于两个的儿子的树. 二叉树节点声明: struct treeNode { elementType element; treeNode * left; treeNod ...

随机推荐

  1. vue 动态添加对象属性

    昨天使用vue发现直接给对象添加属性,并不能触发响应更新,后来看文档发现要通过this.$set 函数动态添加才可用,eg: this.$set( obj, key, data)

  2. nginx部署vue前端,刷新出现404或者500错误的解决方案

    在nginx配置文件的server下加上 try_files $uri $uri/ /index.html; 不加的话是404,路径错误是500,这里的路径只要照着/index.html就行,不用加上 ...

  3. kafka运维填坑

    转载自:https://www.jianshu.com/p/d2cbaae38014 前提: 只针对Kafka 0.9.0.1版本; 说是运维,其实偏重于问题解决; 大部分解决方案都是google而来 ...

  4. Sublime Text 3配置浏览默认路径为localhost

    1.在 Sublime Text 3 中,安装 SideBarEnhancements 侧边栏增强插件.(注意:安装插件之前需要安装包管理工具,参考这里) 2.SideBarEnhancements ...

  5. vue中ref-父主动取值值;

    多用月input标签 定义的时候 直接写ref=“id” <el-input placeholder="请输入内容" style="width: 150px&quo ...

  6. QQ大盗 - 巧用clientkey

    场景: 1.将程序发给好友,好友打开 qq昵称就会被秒改为”账号已被盗“. 2.将程序运行在自己的电脑,让那些随意借用电脑看片聊天的室友产生一个觉悟:乱使用别人电脑很可能会泄露隐私. 思路: 通过数据 ...

  7. JavaJDBC【四、存储过程的使用】

    Mysql还没学到存储过程,不过语法比较简单 此处不深究数据库中的存储过程怎么创建,后面在mysql的学习笔记里再做整理 今天只整理java中如何调用存储过程 语句 CallableStatement ...

  8. MySQL数据库笔记二:数据类型及数据库操作

    三.MySQL数据库数据类型 MySQL数据库中支持多种数据类型:数值型.字符型.日期型 常用的数据类型: 1.整型 int:整形,存储整数 int(M):M表示预期值.与存储大小和数值的范围无关. ...

  9. Delphi MSCom安装

  10. mybatis-03

    mybatis-03 1.mybatis的别名[两种]在MyBatis中可以为变量类型定义别名.简化映射文件的定义,在核心配置文件中定义的别名.别名应用:MyBatis框架先将resultType定义 ...