Week5作业

2023-05-16

A题 最大矩形

题目描述

给一个直方图,求直方图中的最大矩形的面积。例如,下面这个图片中直方图的高度从左到右分别是2, 1, 4, 5, 1, 3, 3, 他们的宽都是1,其中最大的矩形是阴影部分。
在这里插入图片描述
input:
输入包含多组数据。每组数据用一个整数n来表示直方图中小矩形的个数,你可以假定1 <= n <= 100000. 然后接下来n个整数h1, …, hn, 满足 0 <= hi <= 1000000000. 这些数字表示直方图中从左到右每个小矩形的高度,每个小矩形的宽度为1。 测试数据以0结尾。
output:
对于每组测试数据输出一行一个整数表示答案。

样例:
in:
7 2 1 4 5 1 3 3
4 1000 1000 1000 1000
0
out:
8
4000
思路

利用单调栈的思想,得到每一个高度的左右边第一个小于该高度的索引,索引差乘以高度就是矩形面积,比较每一次的大小,输出最大值。
这里具体说一下如何实现单调栈,我使用STL中的stack结构,利用两· 个数组分别储存左右第一个小于该高度的索引,计算右索引时用到的是非递减单调栈,就是说当栈顶元素小于等于待插入元素是才能插入,否则弹栈继续该判断,直至栈空。栈顶元素弹栈,也就意味着栈顶元素已经遇到了右边第一个小于自身的数,更新R[st.top()]。所有的点都加入后,将栈里的所有元素的R值更新为n,即可以延伸到最后。获取左坐标的方法一样,就点的插入顺序变为逆序,即从第n个开始入栈。

代码
#include<iostream>
#include<stdio.h>
#include<stack>
#include<string.h>
#include<algorithm>
#define Max 100000
#define ll long long
using namespace std;
stack<int>st;
ll a[Max+2];
int L[Max+1],R[Max+1],n;
int main()
{
    scanf("%d",&n);
    while(n)
    {
        for(int i=0;i<n;i++)
        scanf("%lld",&a[i]); 
        for(int i=0;i<n;i++)
        { 
            while(!st.empty()&&a[st.top()]>a[i])
            {
                R[st.top()]=i;
                st.pop();
            }
            st.push(i);
        }
        while(!st.empty())
        {
            R[st.top()]=n;
            st.pop();
        }
        for(int i=n-1;i>=0;i--)
        {
            while(!st.empty()&&a[st.top()]>a[i])
            {
                L[st.top()]=i;
                st.pop();
            }
            st.push(i);
        }
        while(!st.empty())
        {
            L[st.top()]=-1;
            st.pop();
        }
        ll mmm=(R[0]-L[0]-1)*a[0];
        for(int i=1;i<n;i++)
        {
            if(mmm<(R[i]-L[i]-1)*a[i])
            mmm=(R[i]-L[i]-1)*a[i];
        }
        printf("%lld\n",mmm);
        cin>>n;
    }
   
    return 0;
}
总结

刚开始没有意识是到数据范围,虽然每个点的数据范围为1e9,但是乘以宽度之后就可能超出int范围,后来改成long long结构后也WA了,百思不得其解,还是基本功不扎实啊,占位符lld错写成了ld,导致连续WA了好几遍。

B题 TT’s Magic Cat

题目描述

Thanks to everyone’s help last week, TT finally got a cute cat. But what TT didn’t expect is that this is a magic cat.
One day, the magic cat decided to investigate TT’s ability by giving a problem to him. That is select nn cities from the world map, and a[i] represents the asset value owned by the ii-th city.
Then the magic cat will perform several operations. Each turn is to choose the city in the interval [l,r] and increase their asset value by c. And finally, it is required to give the asset value of each city after q operations.
Could you help TT find the answer?

input:
The first line contains two integers n,q(1≤n,q≤2·105) — the number of cities and operations.
The second line contains elements of the sequence aa: integer numbers a1,a2,…,an (−106≤ai≤106)
Then q lines follow, each line represents an operation. The ii-th line contains three integers l,r and cc (1≤l≤r≤n,−105≤c≤105) for the i-th operation.
output:
Print n integers a1,a2,…,an one per line, and ai should be equal to the final asset value of the i-th city.

样例:

Input
4 2
-3 6 8 4
4 4 -2
3 3 1
Output
-3 6 9 2
思路

这里采用差分的思想将区间操作转化为对点的操作,首先构造差分数组
p[1]=a[1] p[i]=a[i]-a[i-1]
这样对a的[l,r]区间的增加c的操作就转化为对p[l]+=c,p[r+1]-=c。
最后利用p数组复原出新的a数组然后输出。

代码
#include<iostream>
#include<stdio.h>  
#include<algorithm>
#define Max 300000
#define ll long long
using namespace std; 
ll a[Max+2],n,q,t1,t2,c,s, L[Max+2];
int main()
{
    scanf("%d%d",&n,&q);
    for(int i=1;i<=n;i++)
    scanf("%lld",&a[i]);
    L[1]=a[1];
    for(int i=2;i<=n;i++)
    {
        L[i]=a[i]-a[i-1];
    }
    while(q--)
    {
        scanf("%lld%lld%lld",&t1,&t2,&c);
        L[t1]+=c;
        L[t2+1]-=c;
    }
    
   // printf("%d ",L[1]);
    for(int i=1;i<=n;i++)
    {
        s+=L[i];
        printf("%lld ",s);
    }
    printf("\n");
//    system("pause");
    return 0;
}
总结

这道题也是错在了数据范围上,栽在了A的坑上。

C题 平衡字符串

题目描述

一个长度为 n 的字符串 s,其中仅包含 ‘Q’, ‘W’, ‘E’, ‘R’ 四种字符。
如果四种字符在字符串中出现次数均为 n/4,则其为一个平衡字符串。
现可以将 s 中连续的一段子串替换成相同长度的只包含那四个字符的任意字符串,使其变为一个平衡字符串,问替换子串的最小长度?
如果 s 已经平衡则输出0。
Input一行字符表示给定的字符串s
Output一个整数表示答案

样例

Input
QWER
output
0  
  
Input  
QQWE  
Output 
1
 
Input
QQQW
Output
2  
  
Input  
QQQQ
Output  
3
思路

这里采用尺取法的思想,维护一个双指针,对给定 [L, R],判断是否满足要求? 用 sum1, sum2, sum3, sum4 分别记录不包含区间 [L, R] 这一段时,字符 ‘A’, ‘B’, ‘C’, ‘D’ 的个数 , 先通过替换使 4 类字符数量一致,再判断剩余空闲位置是否 为 4 的倍数 • MAX = max(sum1, sum2, sum3, sum4) , TOTAL = R – L + 1 , FREE = TOTAL [(MAX-sum1)+(MAX-sum2)+(MAX-sum3)+(MAX-sum4)] • 若 FREE ≥0 且为 4 的倍数,则满足要求L++;否则不满足,R++。输出最小的total值。

代码
#include<iostream>
#include<string>
#include<string.h>
#include<stdio.h>
#define MAX 100000
using namespace std;

string str;
int s1,s2,s3,s4,Max,total,Free,L,R,jj=MAX;
int main()
{    
    //scanf("%s",&str[0]);
    cin>>str;
    for(int i=0;i<str.size();i++)
    {
        if(str[i]=='Q')s1++;
        else if(str[i]=='W')s2++;
        else if(str[i]=='E')s3++;
        else if(str[i]=='R')s4++;
    }
    if(s1==s2&&s2==s3&&s3==s4)
    {
        printf("0\n");//exit(0);
           // system("pause");
        return 0;
    }
        if(str[R]=='Q')s1--;
        else if(str[R]=='W')s2--;
        else if(str[R]=='E')s3--;
        else if(str[R]=='R')s4--;

    //R=0 开始
    while(R<str.size())
    {
        Max = max(max(s1,s2),max(s3,s4));
        total = R-L+1;
        Free =total-((Max-s1)+(Max-s2)+(Max-s3)+(Max-s4));
        if(Free>=0&&Free%4==0)//满足条件
        {
            jj=min(jj,total);

            if(str[L]=='Q')s1++;
            else if(str[L]=='W')s2++;
            else if(str[L]=='E')s3++;
            else if(str[L]=='R')s4++;
            L++;
        }
        else 
        {
            R++;
            if(str[R]=='Q')s1--;
            else if(str[R]=='W')s2--;
            else if(str[R]=='E')s3--;
            else if(str[R]=='R')s4--;
        }
    }
    printf("%d\n",jj);
  //  system("pause");
    return 0;
}
总结

对尺取法的理解出了些问题,else里面写错WA了几次,加上对四个计数变量的更新就A了

D滑动窗口

问题描述

ZJM 有一个长度为 n 的数列和一个大小为 k 的窗口, 窗口可以在数列上来回移动. 现在 ZJM 想知道在窗口从左往右滑的时候,每次窗口内数的最大值和最小值分别是多少.
例如:
数列是[1 3 -1 -3 5 3 6 7], 其中 k 等于 3.
input:
输入有两行。第一行两个整数n和k分别表示数列的长度和滑动窗口的大小,1<=k<=n<=1000000。第二行有n个整数表示ZJM的数列。
Output:
输出有两行。第一行输出滑动窗口在从左到右的每个位置时,滑动窗口中的最小值。第二行是最大值。
在这里插入图片描述

样例:
input:
8 3
1 3 -1 -3 5 3 6 7
putput:
-1 -3 -3 -3 3 3
3 3 5 5 6 7
思路

这里用两个单调队列分别计算区域最小值和最大值,这里以区域最小值为例。先往队列中按照非递减序进行入队。对于之后的元素按照同样的规则入队,只不过每次操作都将队首元素作为该区间最小值,最大值原理一样就是入队规则变成小于队尾元素。

代码
#include<iostream>
#include<stdio.h>
#include<deque>
#include<string.h>
#include<algorithm>
#define Max 1000000
using namespace std;
deque<int>qu1,qu2;
int a[Max+2],n,k,c=1,m;
int mi[Max+1],ma[Max+1];
int main()
{
    scanf("%d%d",&n,&k);
    for(int i=0;i<n;i++)
    scanf("%d",&a[i]);
    for(int i=0;i<k-1;i++)
    {
        while(!qu1.empty()&&a[qu1.back()]>a[i])//a[st.top()]>a[i])
        { 
            qu1.pop_back();
        }
        qu1.push_back(i);
        while(!qu2.empty()&&a[qu2.back()]<a[i])//a[st.top()]>a[i])
        { 
            qu2.pop_back();
        }
        qu2.push_back(i);
    }
    for(int i=k-1;i<n;i++,c++)
    {
        while(!qu1.empty()&&a[qu1.back()]>a[i])//a[st.top()]>a[i])
        { 
            qu1.pop_back();
        }
        qu1.push_back(i);
        while(!qu2.empty()&&a[qu2.back()]<a[i])//a[st.top()]>a[i])
        { 
            qu2.pop_back();
        }
        qu2.push_back(i); 
        mi[m]=qu1.front();
        ma[m++]=qu2.front();
        if(qu1.front()<=i-k+1)qu1.pop_front();
        if(qu2.front()<=i-k+1)qu2.pop_front();
    }
    for(int i=0;i<m;i++)
        printf("%d ",a[mi[i]]);
    printf("\n");
    for(int i=0;i<m;i++)
        printf("%d ",a[ma[i]]);
    printf("\n");
   // system("pause");
    return 0;
}
总结

在判定队首元素是否应该出队的时候犯了一点小错,因为队列中存储的是数组的索引,所以只需要判断该值与i的差是否大于k就好了

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Week5作业 的相关文章

  • 2.4G&5G WiFi 5V供电大短路,维修更换5G芯片

    故障类别 xff1a 无WiFi信号 故障现象 xff1a 漏电 xff0c 无2 4G和5GWiFi 故障描述 xff1a 开机后发现电流比其它板子大一点 xff0c 并且无异常发热情况 附件 xff1a 分析过程 xff1a 根据故障找
  • 路由器不开机——维修更换MT7621AT CPU

    故障类别 xff1a 不开机 故障现象 xff1a 210mA横流不开机 故障描述 xff1a 发现CPU异常发烫不开机 xff0c 其它地方未有发热现象 附件 xff1a 原因分析 xff1a 开机测量各路电压 xff0c 发现均有电压
  • 编译QT 5.9.7 msvcr2013 x86 32位版本

    因为项目需要 xff0c 用到了qt msvcr2013 x86 版本 但是官方下载的qt安装包里面只有x64的 xff0c 因此决定自己编译x86的版本 编译所需要的工具 xff1a qt源码包 xff0c python xff0c vs
  • <C语言>打印 n 阶魔方阵( n 为奇数),魔方阵的每一行、每一列和对角线元素之和都相等

    打印魔方阵 xff0c 首先我们得知道魔方阵的编写规律 xff1a 魔方阵的填充规律如下 xff1a 假设当前创建了一个矩阵 span class token keyword int span matrix span class token
  • 矩阵连乘之求最优值与构造最优解——呕心沥血篇

    矩阵连乘 详细讲解 初次接触dp xff0c 就看到很多位大佬给出自己的见解 xff0c dp算是最难的算法之一吧 xff0c 主要在于灵活度高 xff0c 需要自己推出动态规划方程 100个动态规划方程传送门涉及到dp问题那么for循环一
  • (C)数组,指针

    数组 xff1a int a 8 指针数组 xff0c 每个单元存放一个指针 每个指针是占8个字节在64位 xff0c 32位占4个字节 int xff08 a xff09 8 数组指针 xff0c 一个指向数组的指针 数组定义 xff1a
  • week5 单调栈 最大矩形

    Titile 给一个直方图 xff0c 求直方图中的最大矩形的面积 例如 xff0c 下面这个图片中直方图的高度从左到右分别是2 1 4 5 1 3 3 他们的宽都是1 xff0c 其中最大的矩形是阴影部分 Input 输入包含多组数据 每
  • ERROR 1238 (HY000): Variable ‘secure_file_priv‘ is a read only variable

    在进行数据导出操作的时候 xff0c 报错 xff1a ERROR 1238 HY000 Variable secure file priv is a read only variable 该变量是可读的 xff0c 不能用set设置 xf
  • kali安装目录扫描工具-dirsearch和git泄露利用脚本GitHack

    目录扫描工具 dirsearch 下载dirsearch git clone https github com maurosoria dirsearch 进入dirsearch目录 xff0c 进行扫描 这里我尝试了几次不同的用法 xff0
  • C语言—写一个函数求unsigned int型变量x在内存中二进制1的个数

    题目 xff1a 写一个函数求unsigned int型变量x在内存中二进制1的个数 思路 xff1a 先把num除2取余 xff0c 余数为1 xff0c count 43 43 再让num 61 num 2 取整 循环 xff0c 直到
  • Proteus 8.9下载安装指南

    因为Keil中的代码需要进行仿真 xff0c 除了用实际的开发板 xff0c 仿真软件也很实用 虽然已经装了AD xff0c 但是网上关于AD仿真的资料相对较少 今天装一个Proteus用用 安装包 xff1a Proteus8 9 提取码
  • STM32烧录

    资源包 xff1a STLink驱动 软件包 提取码 xff1a cgcg 结构 xff1a 通过RX TX脚连接到MCU芯片串口引脚 xff0c USB串口转换器 xff08 USB TTL的电路 xff09 一边连接RX TX引脚 xf
  • stm32使用串口进行通讯之发送数据

    前提准备 xff1a 1 库函数基础模板 2 stlink下载器 USB TTL下载器 单片机最小开发板stm32F103C8T6 3 面包板及相关接线 4 vscode与keil的联合开发更流畅 5 串口软件 xff0c 这个下面视频有
  • ubuntu 16.04挂载磁盘,开机丢失

    一般磁盘可能要先格式化为指定格式 sudo mkfs t ext4 dev sdb1 直接mount磁盘分区 xff0c 比如 sudo mount dev sdb1 var 当时起作用了 xff0c 但是reboot之后 xff0c 就会
  • stm32使用外部flash w25Q128实现读写操作

    前言 数据保存是所有项目的基本功能 xff0c 但是对于STM32C8T6的原flash进行操作 xff0c 一方面大小有可能不够 xff0c 另一方面单片机的运行程序本来就放在这个里面 xff0c 所以还是外接的好 这里选用w25Q128
  • Keil(MDK)STM32和51版本详细安装

    前言 保姆级教程 xff0c 多次反复安装 xff0c 实测可用 链接包失效可留言 安装注意 keil公司被ARM公司收购 xff0c 收购后就改名MDK xff0c 所以keil的下载包也是以MDK命名 安装路径不能带有中文 目录不能和5

随机推荐

  • STM32 使用LCD12864显示屏(串行方式)

    LCD12864 简介 12864LCD液晶显示模块是一款4位 8位并行 2线或3线接口方式 xff0c 内部含有国际一级 二级简体中文字库的图形点阵液晶模块 显示分辨率为12864 xff0c 内置8198个1616点汉字 xff0c 和
  • 快速学习C语言指针操作

    一 了解底层 指针说到底是在对数据进行操作 先了解数据的存储 xff0c 看看指针操作的位置 一位数据的存储 xff1a 将一位数据置1 xff0c 如图所示 xff0c 首先地址位需要置1 xff0c 再将数据输入位置1 xff0c 那么
  • MG90S 舵机180°角度驱动

    MG90S简介 舵机 xff1a 是一种角度伺服电机 xff0c 一般是由齿轮组 电位器 舵机控制电路 直流电机构成 由发送控制信号来控制输出轴的位置 数字舵机与模拟舵机的区别 xff1a MG90S是一款常用的数字舵机 xff0c 还有一
  • MPU6050 6轴姿态传感器的分析与使用(一)

    一 MPU6050简介 MPU6050是一个6轴姿态传感器 xff08 3轴加速度计和3轴陀螺仪传感器 xff09 xff0c 可以测量芯片自身X Y Z轴的加速度 角度参数 xff0c 通过数据融合 xff0c 可以得到姿态角 二 简介分
  • 基于51单片机的步进电机驱动,亲测无误

    文章目录 前言一 我们该如何实现电机驱动 xff1f 二 驱动实现1 硬件准备2 软件编写3 实物 总结 前言 这一次要分享的项目是最近接单做的一个小玩意儿 xff0c 基于51单片机的步进电机驱动 最近积压了两个月的小项目会在后面陆续发出
  • 对 string 类的输入(直接看总结)

    一 简述 cin get 和 cin getline 解决 char 中的问题 xff0c 遇到换行符时才停止 对于 string 类 xff0c 不能使用cin get 和cin getline 进行输入 xff0c 会报错 xff0c
  • C++中字符串的比较(针对C-风格字符串)

    一 简述 在头文件 lt cstring gt 中 xff0c 有一个函数strcmp 二 详细介绍 strcmp 比较字符串 格式为 strcmp const char Str1 const char Str2 xff0c 由此可见 xf
  • 关于文件结束符EOF

    一 简述 我们知道 xff0c C 43 43 中可以通过cin xff0c cin get xff0c cin getline xff0c getline 等对字符串进行输入 xff08 若对这些输入模糊 xff0c 可以阅读这篇文章 x
  • ubuntu 1810上snap安装nextcloud

    尝试在ubuntu1810上安装nextcloud 因为服务器配置好了xrdp远程访问 xff0c 所以直接准备在sofware center进行安装 安装了半天却提示 unable to install nextcloud snap xx
  • 关于cout 输出 char 型字符 ++ch和 ch+1 不同的结果(直接看详解)

    一 简述 今天在做练习题时注意到了之前所没有注意到的问题 xff1a 若给同样的 ch xff0c cout lt lt 43 43 ch 与 cout lt lt ch 43 1 输出后的结果不一样 浅思之后明白了 xff0c 其实这个现
  • C++定义与声明

    一 简述 什么是定义 xff1f 什么是说明 xff1f 相信很多小伙伴都对这两个概念模糊不清 xff0c 下面我就对其简单介绍一下 二 详细说明 定义 全称为定义声明 xff0c 给变量分配空间 声明 全称为引用声明 xff0c 不给变量
  • MySQL学习日记(六)用户管理、权限安全

    文章目录 用户管理和权限安全1 user权限表1 1 用户列1 2 权限列1 3 安全列1 4 资源控制列 2 其他权限表 xff08 db tables priv columns priv procs priv xff09 2 1 db表
  • Linux上的网络配置——bonding配置

    网络接口配置bonding Bonding 将多块网卡绑定同一IP地址对外提供服务 xff0c 可以实现高可用或者负载均衡 直接给两块网卡设置同一IP地址是不可以的 通过bonding xff0c 虚拟一块网卡对外提供连接 xff0c 物理
  • python--直接通过cmd找到pip所安装库的位置

    https blog csdn net weixin 44345862 article details 87003478
  • 家中闲置旧电脑改装家用NAS(入门教程)

    家中闲置旧电脑改装家用NAS xff08 纯小白入门教程 xff09 什么是NAS xff1f NAS的基本知识在国内的常用品牌 NAS品牌的配置问题作者的硬件配置 装机正文准备工作旧电脑的准备工作 xff08 已经完成或无这方面问题的可跳
  • 适用于 Linux 的 Windows 子系统 (WSL)

    适用于 Linux 的 Windows 子系统 xff08 WSL xff09 描述什么是 适用于 Linux 的 Windows 子系统 系统要求Windows 10 Windows 11 查看计算机系统的版本 虚拟化功能启用虚拟化功能禁
  • python爬取4399页面

    提示 xff1a 该段代码只可爬取4399页面的代码和图片 xff0c 适合新手爬虫入门学习 python爬取4399页面 代码总结 代码 代码如下 xff1a import urllib span class token punctuat
  • Arduino手动安装esp8266开发板

    Arduino手动安装esp8266开发板可以用离线安装包 xff0c 确定就是离线安装包网上不好找 xff0c 版本也不齐全 xff0c 无法找到某个特定版本的离线安装包 xff0c 好处是直接双击运行 xff0c 傻瓜式安装就好了 xf
  • 修改启动的进程的窗口标题

    最近在改一个项目里的小功能 原先的情况是在网页上点击按钮 xff0c ocx控件写临时 rdp文件 xff0c 根据这个文件启动mstsc exe 现在要做的工作是把远程桌面连接窗口的标题改成能显示特定信息的标题 感谢 http blog
  • Week5作业

    A题 最大矩形 题目描述 给一个直方图 xff0c 求直方图中的最大矩形的面积 例如 xff0c 下面这个图片中直方图的高度从左到右分别是2 1 4 5 1 3 3 他们的宽都是1 xff0c 其中最大的矩形是阴影部分 input 输入包含