转移dp简单数学数论

news2025/5/25 22:36:11

1.转移dp问题

昨天的练习赛上有一个很好玩的起终点问题,第一时间给出bfs的写法。

但是写到后面发现不行,还得是的dp转移的写法才能完美的解决这道题目。

每个格子可以经过可以不经过,因此它的状态空间是2^(n*m),但是n,m的数据范围是500,显然是不可取的。bfs适用于计数或者最短距离,而不是最大和或最优路径问题。

故:对于最大和的问题dp是最合适的选择。

题目意思:

给定起点终点,每个点只能经过一次,找到最大的路径和,并且只能向下向右走动。

思路:

既然是dp那么一点有初始化,很容易想到第一列一定是固定的,因为该列只能像下走动(从起始点开始)。

那么之后我们就对每一列赋值(从第一列开始,每一列的状态都是从前面一列转移过来的)。

对于某一列的赋值,我们可以从头开始往下走,也可以是从尾开始走到第一行在进行继续走,那么这里就分成了两种情况。

我们先任意求出一种情况,然后在慢慢的用前缀和进行维护(因为是一条线下的,前缀和维护方便)。(毕)

#include<bits/stdc++.h>
using namespace std;
#define int long long
const int nima=8e18;
int a[504][504];
void solve(){
    int n,m;
    cin>>n>>m;
    int s,t;
    cin>>s>>t;s--,t--;
    for(int i=0;i<n;i++){
        for(int j=0;j<m;j++){
            cin>>a[i][j];
        }
    }
    vector<vector<int>> dp(n,vector<int>(m,-nima));
    //这里的dp[i][j]的意思是从[s][0]开始到[i][j]的最大贡献
    // 初始化第一列的值
    int sum=a[s][0];
    for(int i=s;;){//一共要遍历s次
        dp[i][0]=sum;  // 初始化环形路径的第一个点
        i=(i+1)%n;     // 环形移动
        sum+=a[i][0];   // 累加路径上的值
        if(i==s) break; // 回到起点时结束
    }
    // 动态规划处理每一列
    for(int i=1;i<m;i++){
        int cnt=-nima;
        int sum=0;
        vector<int> pre(n);  // 前缀和数组
        // 正向遍历,计算从上方转移的最大值
        for(int j=0;j<n;j++){
            cnt=max(cnt,dp[j][i-1]-sum);  // 维护最大值,从左边过来的
            sum+=a[j][i];                   // 累加当前列的值
            dp[j][i]=cnt+sum;              
            pre[j]=sum;                     // 记录前缀和,这个sum是列环形状态下的前缀和
        }
        cnt=-nima;
        // 反向遍历,处理环形路径的情况
        for(int j=n-1;j>=0;j--){
            if(j!=n-1) dp[j][i]=max(dp[j][i],cnt+pre[j]);
            // 计算从下方转移的最大值(考虑环形路径)
            if(j!=0) cnt=max(cnt,dp[j][i-1]+pre[n-1]-pre[j-1]);
        }
    }
    cout<<dp[t][m-1]<<endl;
}

signed main(){
    int ac=1;
    while(ac--)  solve();
    return 0;
}

2.简单数学

这次的团队赛有个简单数学问题,挺有意思的。

题目意思:

给出一个数组,找出最大贡献(每个贡献是相邻两个数字之差的绝对值)。

思路:

我们可以根据题目给的样例找到....

1 2 3 4 5 6 的最大贡献是9,即(3,4)(2,5) (1,6)状态下贡献是最大的。

我们进行改变之后发现....

3 2 1 4 5 6的最大贡献也是9,即(1,4)(2,5)(3,6)状态下贡献是最大的。

之后在进行任意举列子之后我们发现....

一组数据进行排序后每次最大贡献取法是首位找(毕)

小tips:数学问题,大胆猜,先排序,然后...(看看能不能瞎猫碰到死耗子)

#include<bits/stdc++.h>
using namespace std;
#define int long long

inline void solve(){
    int n; cin >> n;
    vector<int> a(2 * n);
    for(int i = 0; i < 2 * n; i++) cin >> a[i];
    sort(a.begin(), a.end());
    //排序
    int answer = 0;
    for(int i = 0; i < n; i++) {
        answer+= abs(a[i] - a[2 * n - 1 - i]);
        //首位之差,参考1 2 3 4 5 6这个样例
    }
    cout << answer << endl;
}

signed main(){
    ios::sync_with_stdio(0);
    cin.tie(0);
    cout.tie(0);
    int t; cin >> t;
    while(t--) solve();
    return 0;
}

3.数论

这次的数论有点点绕...

 题目意思:

给定一个数是好数m,只有m形如k!或者为偶数的条件下才成立。

给定一个数a,找到最少的分类情况k,使得k个好数之后是a。

思路:

观察题目的数据范围我们看到,n<=10^12,而且有t组数据,最好做一个状态压缩。

我们先对阶乘进行赋初值,15!>10^12。

每次减去1到15的阶乘,最后加上二进制中1的个数就是答案,每次枚举维护一个最小值即可。(毕)

#include <bits/stdc++.h>
using namespace std;
#define int long long 
#define pii pair<int, int> 
vector<int> v;


inline void solve() {
    int sum = 1,i=1;  // 初始化阶乘结果为 1
    while(sum<=1e12){
        sum*=i++;
        v.push_back(sum);
    }
    //sort(v.begin(), v.end());  // 对向量 v 进行排序
    // 去除重复的阶乘结果
    //v.erase(unique(v.begin(), v.end()), v.end());
    int m = v.size();  
    int n;
    cin >> n; 
    int ans = 1e9 + 7;
    // 遍历所有可能的子集(通过位掩码的方式)
    for (int i = 0; i <= (1 << m) - 1; i++) {
        int res = n;  // 初始化 res 为 n
        // 遍历每一位,检查是否在子集中
        for (int j = 0; j < m; j++) {
            if ((1 << j) & i)  // 如果第 j 位在子集 i 中
                res -= v[j];  // 从 res 中减去对应的阶乘值
        }
        if (res < 0) continue;  // 如果 res 为负数,跳过当前子集

        // 计算当前子集的位数和剩余数的位数之和,并更新最小值
        ans = min(ans, (int)__builtin_popcountll(res) + __builtin_popcountll(i));
    }
    cout << ans << endl;
}
signed main() {
    int nc;
    cin >> nc;
    while (nc--) solve();  
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2385656.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

动静态库--

目录 一 静态库 1. 创建静态库 2. 使用静态库 2.1 第一种 2.2 第二种 二 动态库 1. 创建动态库 2. 使用动态库 三 静态库 VS 动态库 四 动态库加载 1. 可执行文件加载 2. 动态库加载 一 静态库 Linux静态库&#xff1a;.a结尾 Windows静态库&#xff1a;.lib结尾…

git clone时出现无法访问的问题

git clone时出现无法访问的问题 问题&#xff1a; 由于我的git之前设置了代理&#xff0c;然后在这次克隆时又没有打开代理 解决方案&#xff1a; 1、如果不需要代理&#xff0c;直接取消 Git 的代理设置&#xff1a; git config --global --unset http.proxy git config --gl…

文件系统·linux

目录 磁盘简介 Ext文件系统 块 分区 分组 inode 再谈inode 路径解析 路径缓存 再再看inode 挂载 小知识 磁盘简介 磁盘&#xff1a;一个机械设备&#xff0c;用于储存数据。 未被打开的文件都是存在磁盘上的&#xff0c;被打开的加载到内存中。 扇区&#xff1a;是…

【Matlab】雷达图/蛛网图

文章目录 一、简介二、安装三、示例四、所有参数说明 一、简介 雷达图&#xff08;Radar Chart&#xff09;又称蛛网图&#xff08;Spider Chart&#xff09;是一种常见的多维数据可视化手段&#xff0c;能够直观地对比多个指标并揭示其整体分布特征。 雷达图以中心点为原点&…

使用JProfiler进行Java应用性能分析

文章目录 一、基本概念 二、Windows系统中JProfiler的安装 1、下载exe文件 2、安装JProfiler 三、JProfiler的破解 四、IDEA中配置JProfiler 1、安装JProfiler插件 2、关联本地磁盘中JProfiler软件的执行文件 3、IDEA中启动JProfiler 五、监控本地主机中的Java应用 …

遥感解译项目Land-Cover-Semantic-Segmentation-PyTorch之一推理模型

文章目录 效果项目下载项目安装安装步骤1、安装环境2、新建虚拟环境和安装依赖测试模型效果效果 项目下载 项目地址 https://github.com/souvikmajumder26/Land-Cover-Semantic-Segmentation-PyTorch 可以直接通过git下载 git clone https://github.com/souvikmajumder26/Lan…

六、【前端启航篇】Vue3 项目初始化与基础布局:搭建美观易用的管理界面骨架

【前端启航篇】Vue3 项目初始化与基础布局&#xff1a;搭建美观易用的管理界面骨架 前言技术选型回顾与准备准备工作第一步&#xff1a;进入前端项目并安装 Element Plus第二步&#xff1a;在 Vue3 项目中引入并配置 Element Plus第三步&#xff1a;设计基础页面布局组件第四步…

C++ 前缀和数组

一. 一维数组前缀和 1.1. 定义 前缀和算法通过预处理数组&#xff0c;计算从起始位置到每个位置的和&#xff0c;生成一个新的数组&#xff08;前缀和数组&#xff09;。利用该数组&#xff0c;可以快速计算任意区间的和&#xff0c;快速求出数组中某一段连续区间的和。 1.2. …

细胞冻存的注意事项,细胞冻存试剂有哪些品牌推荐

细胞冻存的原理 细胞冻存的基本原理是利用低温环境抑制细胞的新陈代谢&#xff0c;使细胞进入一种“休眠”状态。在低温条件下&#xff0c;细胞的生物活动几乎停止&#xff0c;从而实现长期保存。然而&#xff0c;细胞在冷冻过程中可能会因为细胞内外水分结冰形成冰晶而受损。…

快速上手Linux火墙管理

实验网络环境&#xff1a; 主机IP网络f1192.168.42.129/24NATf2&#xff08;双网卡&#xff09; 192.168.42.128/24 192.168.127.20/24 NAT HOST-NOLY f3192.168.127.30/24HOST-ONLY 一、iptables服务 1.启用iptables服务 2.语法格式及常用参数 语法格式&#xff1a;参数&…

[创业之路-375]:企业战略管理案例分析 - 华为科技巨擘的崛起:重构全球数字化底座的超级生命体

在人类文明从工业时代&#xff08;机械、电气、自动化&#xff09;迈向数字智能&#xff08;硬件、软件、算法、虚拟、智能&#xff09;时代的临界点上&#xff0c;一家中国企业正以令人震撼的姿态重塑全球科技版图。从通信网络的底层架构到智能终端的生态闭环&#xff0c;从芯…

AI基础知识(05):模型提示词、核心设计、高阶应用、效果增强

目录 一、核心设计原则 二、高阶应用场景 三、突破性技巧 以下是针对DeepSeek模型的提示词设计思路及典型应用场景示例&#xff0c;帮助挖掘其潜在能力&#xff1a; 一、核心设计原则 1. 需求明确化&#xff1a;用「角色定位任务目标输出格式」明确边界 例&#xff1a;作为历…

推测解码算法在 MTT GPU 的应用实践

前言​ 目前主流的大模型自回归解码每一步都只生成一个token, 尽管kv cache等技术可以提升解码的效率&#xff0c;但是单个样本的解码速度依然受限于访存瓶颈&#xff0c;即模型需要频繁从内存中读取和写入数据&#xff0c;此时GPU的利用率有限。为了解决这种问题&#xff0c;…

Axure酒店管理系统原型

酒店管理系统通常被设计为包含多个模块或界面&#xff0c;以支持酒店运营的不同方面和参与者。其中&#xff0c;管理端和商户端是两个核心组成部分&#xff0c;它们各自承担着不同的职责和功能。 软件版本&#xff1a;Axure RP 9 预览地址&#xff1a;https://556i1e.axshare.…

写实交互数字人在AI招聘中的应用方案

随着科技的进步&#xff0c;越来越多的行业开始探索如何利用人工智能提升效率和服务质量。其中&#xff0c;写实交互数字人技术以其高度拟真的交互体验和丰富的情感表达能力&#xff0c;在人力资源领域特别是招聘环节中展现出了巨大潜力。本文将探讨写实交互数字人在AI招聘中的…

房贷利率计算前端小程序

利率计算前端小程序 视图效果展示如下&#xff1a; 在这里插入代码片 <!DOCTYPE html> <html lang"zh-CN"> <head><meta charset"UTF-8"><meta name"viewport" content"widthdevice-width, initial-scale1.0&qu…

在Visual Studio中进行cuda编程

首先下载与CUDA Toolkit匹配的Visual Studio版本 比如我的CUDA Toolkit版本是12.6&#xff0c;那么我可以使用2022的Visual Studio。 查看Toolkit版本 nvcc -V 配置 ok&#xff0c;让我们开始Visual Studio的nvcc编译器配置 参考例文https://github.com/apachecn/succinc…

Fastrace:Rust 中分布式追踪的现代化方案

原文链接&#xff1a;Fastrace: A Modern Approach to Distributed Tracing in Rust | FastLabs / Blog 摘要 在微服务架构中&#xff0c;分布式追踪对于理解应用程序的行为至关重要。虽然 tokio-rs/tracing 在 Rust 中被广泛使用&#xff0c;但它存在一些显著的挑战&#xf…

Linux云计算训练营笔记day13【CentOS 7 find、vim、vimdiff、ping、wget、curl、RPM、YUM】

Linux云计算训练营笔记day13[CentOS 7 find、vim、vimdiff、ping、wget、curl、RPM、YUM]] 目录 Linux云计算训练营笔记day13[CentOS 7 find、vim、vimdiff、ping、wget、curl、RPM、YUM]]1.find练习2.vim高级使用2.1 命令模式:2.2 插入模式:2.3 末行模式: 3. vimdiff4. ping5.…

黑马Java基础笔记-15

Set 无索引&#xff0c;无序&#xff0c;不可重复 HashSet object类中默认hashCode的方法是根据地址值。 如果集合中存储的是自定义对象&#xff0c;必须要重写hashCode和equals方法。 底层原理 jdk8以前&#xff1a;数组 链表 jdk8及以后&#xff1a;数组 链表 红黑…