[AHOI2009] 维护序列

[AHOI2009] 维护序列

题目背景

老师交给小可可一个维护数列的任务,现在小可可希望你来帮他完成。

题目描述

有一个长为 n n n 的数列 { a n } \{a_n\} {an},有如下三种操作形式:

  1. 格式 1 t g c,表示把所有满足 t ≤ i ≤ g t\le i\le g tig a i a_i ai 改为 a i × c a_i\times c ai×c ;
  2. 格式 2 t g c 表示把所有满足 t ≤ i ≤ g t\le i\le g tig a i a_i ai 改为 a i + c a_i+c ai+c ;
  3. 格式 3 t g 询问所有满足 t ≤ i ≤ g t\le i\le g tig a i a_i ai 的和,由于答案可能很大,你只需输出这个数模 p p p 的值。

输入格式

第一行两个整数 n n n p p p

第二行含有 n n n 个非负整数,表示数列 { a i } \{a_i\} {ai}

第三行有一个整数 m m m,表示操作总数。

从第四行开始每行描述一个操作,同一行相邻两数之间用一个空格隔开,每行开头和末尾没有多余空格。

输出格式

对每个操作 3,按照它在输入中出现的顺序,依次输出一行一个整数表示询问结果。

样例 #1

样例输入 #1

7 43
1 2 3 4 5 6 7
5
1 2 5 5
3 2 4
2 3 7 9
3 1 3
3 4 7

样例输出 #1

2
35
8

提示

样例输入输出 1 解释
  • 初始时数列为 { 1 , 2 , 3 , 4 , 5 , 6 , 7 } \{1,2,3,4,5,6,7\} {1,2,3,4,5,6,7}
  • 经过第 1 1 1 次操作后,数列为 { 1 , 10 , 15 , 20 , 25 , 6 , 7 } \{1,10,15,20,25,6,7\} {1,10,15,20,25,6,7}
  • 对第 2 2 2 次操作,和为 10 + 15 + 20 = 45 10+15+20=45 10+15+20=45,模 43 43 43 的结果是 2 2 2
  • 经过第 3 3 3 次操作后,数列为 { 1 , 10 , 24 , 29 , 34 , 15 , 16 } \{1,10,24,29,34,15,16\} {1,10,24,29,34,15,16}
  • 对第 4 4 4 次操作,和为 1 + 10 + 24 = 35 1+10+24=35 1+10+24=35,模 43 43 43 的结果是 35 35 35
  • 对第 5 5 5 次操作,和为 29 + 34 + 15 + 16 = 94 29+34+15+16=94 29+34+15+16=94,模 43 43 43 的结果是 8 8 8
数据规模与约定

测试数据规模如下表所示:

数据点编号123456789,10
n = n= n= 10 10 10 1000 1000 1000 1000 1000 1000 10000 10000 10000 60000 60000 60000 70000 70000 70000 80000 80000 80000 90000 90000 90000 100000 100000 100000
m = m= m= 10 10 10 1000 1000 1000 1000 1000 1000 10000 10000 10000 60000 60000 60000 70000 70000 70000 80000 80000 80000 90000 90000 90000 100000 100000 100000

对于全部的测试点,保证 0 ≤ p , a i , c ≤ 1 0 9 0 \leq p, a_i, c \leq 10^9 0p,ai,c109 1 ≤ t ≤ g ≤ n 1 \leq t \leq g \leq n 1tgn

代码

#include <bits/stdc++.h>
using namespace std;
#define int long long
#define rc(x) ((x<<1)|1)
#define lc(x) (x<<1)
const int M = 1e6;
const int N = 1e18;
int a[M], n, m, mod;
void read() {
	cin >> n >> mod;
	for (int i = 1; i <= n; i++) cin >> a[i]; 
	cin >> m ;
}
struct node {
	int sum, mul, add;
};
struct segment {
	node seg[M << 2];
	void push_up(int x) {
		seg[x].sum = (seg[lc(x)].sum + seg[rc(x)].sum) % mod;
	}
	void build(int o, int l, int r) {
		seg[o].mul = 1; seg[o].add = 0;
		if (l == r) {
			seg[o].sum = a[l];
			return;
		}
		int mid = (l + r) >> 1;
		build(lc(o), l, mid);
		build(rc(o), mid + 1, r);
		push_up(o);
	}
	void f(int o, int l, int r, int add, int mul) {
		seg[o].mul = (seg[o].mul * mul) % mod;
		seg[o].add = (seg[o].add * mul) % mod;
		seg[o].add = (seg[o].add + add) % mod;
		seg[o].sum = (seg[o].sum * mul) % mod;
		seg[o].sum = (seg[o].sum + (r - l + 1) * add) % mod;
	}
	void push_down(int o, int l, int r) {
		int mid = (l + r) >> 1;
		f(lc(o), l, mid, seg[o].add, seg[o].mul);
		f(rc(o), mid + 1, r, seg[o].add, seg[o].mul);
		seg[o].add = 0; seg[o].mul = 1;
	}
	void update(int ql, int qr, int add, int mul, int o = 1, int l = 1, int r = n) {
		if (ql <= l and r <= qr) { f(o, l, r, add, mul); return; }
		int mid = (l + r) >> 1;
		push_down(o, l, r);
		if (ql <= mid) update(ql, qr, add, mul, lc(o), l, mid);
		if (qr >= 1 + mid)update(ql, qr, add, mul, rc(o), mid + 1, r);
		push_up(o);
	}
	int query(int ql, int qr, int o = 1, int l = 1, int r = n) {
		if (ql <= l and r <= qr) return seg[o].sum;
		int mid = (l + r) >> 1, ans = 0;
		push_down(o, l, r);
		if (ql <= mid) ans = (ans + query(ql, qr, lc(o), l, mid)) % mod;
		if (mid + 1 <= qr) ans = (ans + query(ql, qr, rc(o), mid + 1, r)) % mod;
		push_up(o);
		return ans%mod;
	}
}T1;
void solve() {
	int opt, x, y, k;
	cin >> opt >> x >> y;
	switch (opt) {
	case 1: {
		cin >> k;
		T1.update(x, y, 0, k);
		break;
	}
	case 2: {
		cin >> k;
		T1.update(x, y, k, 1);
		break;
	}
	default:cout << T1.query(x, y) << endl;
	}
}
signed main() {
	ios::sync_with_stdio(false);
	read();
	T1.build(1, 1, n);
	while (m--) solve();
	return 0;
}

说明

实现支区间加、区间乘和区间求和

  1. #define int long longint 类型重定义为 long long 类型

  2. #define rc(x) ((x<<1)|1)#define lc(x) (x<<1) 定义了计算线段树左右子节点下标的宏。

  3. 全局数组 a[M] 存储原始数据,n 表示数据规模,m 表示操作次数,mod 用于取模运算。

  4. node 结构体定义了线段树节点的三个属性:sum 表示区间和,mul 表示乘法懒惰标记,add 表示加法懒惰标记。

  5. segment 结构体封装了线段树的主要操作:

    • push_up(int x) 用于更新节点 xsum 值,通过其左右子节点的 sum 值计算得出。
    • build(int o, int l, int r) 是线段树的构建函数,采用递归方式构建。
    • push_down(int o, int l, int r) 用于下推节点 o 的懒惰标记到其左右子节点。
    • update(int ql, int qr, int add, int mul, int o, int l, int r) 是线段树的更新函数,用于更新区间 [ql, qr] 上的值,可以是加法或乘法更新。
    • query(int ql, int qr, int o, int l, int r) 是线段树的查询函数,用于查询区间 [ql, qr] 的和。

需要注意乘法的优先级更高,处理好加乘关系

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

C++ sort排序

sort函数接受两个迭代器作为参数&#xff0c;分别表示要排序的范围的起始和结束位置。 请注意&#xff0c;sort函数默认使用小于运算符&#xff08;<&#xff09;来比较元素的顺序&#xff0c;默认从小到大排。 在这里&#xff0c;使用str.begin()和str.end()来表示整个字符…

华为机试-算法一

寻找身高相近的小朋友 小明今年升学到了小学1年纪来到新班级后&#xff0c;发现其他小朋友身高参差不齐 然后就想基于各小朋友和自己的身高差&#xff0c;对他们进行排序请帮他实现排序 输入描述 第一行为正整数 h和n 0<h<200 为小明的身高 0<n<50 为新班级其他小…

Muduo库编译学习(1)

1.muduo库简介 muduo是由Google大佬陈硕开发&#xff0c;是一个基于非阻塞IO和事件驱动的现代C网络库&#xff0c;原生支持one loop per thread这种IO模型&#xff0c;该库只支持Linux系统&#xff0c;网上大佬对其褒贬不一&#xff0c;作为小白用来学习就无可厚非了。 git仓库…

阅读笔记 | Transformers in Time Series: A Survey

阅读论文&#xff1a; Wen, Qingsong, et al. “Transformers in time series: A survey.” arXiv preprint arXiv:2202.07125 (2022). 这篇综述主要对基于Transformer的时序建模方法进行介绍。论文首先简单介绍了Transformer的基本原理&#xff0c;包括位置编码、多头注意力机…

二十三、剖析 LinkedList

剖析 LinkedList 本文为书籍《Java编程的逻辑》1和《剑指Java&#xff1a;核心原理与应用实践》2阅读笔记 ArrayList随机访问效率很高&#xff0c;但插入和删除性能比较低&#xff1b;LinkedList同样实现了List接口&#xff0c;它的特点与ArrayList几乎正好相反。除了实现了L…

springboot240基于Spring boot的名城小区物业管理系统

基于Spring boot的名城小区物业管理系统的设计与实现 摘要 当下&#xff0c;正处于信息化的时代&#xff0c;许多行业顺应时代的变化&#xff0c;结合使用计算机技术向数字化、信息化建设迈进。以前相关行业对于物业信息的管理和控制&#xff0c;采用人工登记的方式保存相关数…

来不及了!大学必须完成的四件事!

老师们常说&#xff0c;上大学就轻松了 其实不然 大学不是人生的终点&#xff0c;而是新的起跑线 不是休息站&#xff0c;而是进入社会的最后冲刺跑道 大学生活苦乐参半&#xff0c;成人世界即将来临 出了校门&#xff0c;你会发现社会复杂多变&#xff0c;需要不断学习 稍…

社区店选址评估:利用大数据选址的技巧与策略

在当今数字化的时代&#xff0c;利用大数据进行社区店选址评估已成为一种高效、科学的方法。作为一名开鲜奶吧5年的创业者&#xff0c;我将分享一些利用大数据选址的技巧与策略&#xff0c;帮助你找到最适合的店铺位置。 1、确定目标商圈 在选址之前&#xff0c;首先要明确自己…

airTest连接雷电模拟器后,打开横屏游戏,airTest设备窗显示游戏是横屏,雷电模拟器却显示竖屏

目录 airTest连接雷电模拟器后&#xff0c;打开横屏游戏&#xff0c;airTest设备窗显示游戏是横屏&#xff0c;雷电模拟器却显示竖屏 原因&#xff1a;雷电模拟器4会出现兼容性问题。 解决&#xff1a;升级到雷电模拟器9.0.66(9)&#xff0c;可解决该问题。

输出梯形 C语言

解析&#xff1a;这个输出图形的题就是一个找规律加数学计算&#xff0c;我们发现每行比上一行多两个*&#xff0c;最后一行的*表达式为h&#xff08;h-1&#xff09;*2&#xff0c;即3*h-2&#xff0c;那么每一行就是一个先输出最后一行&#xff0d;当前行*个数个空格&#xf…

用Java语言创建的Spring Boot项目中,如何传递List集合呢?

前言&#xff1a; 在上篇文章中&#xff0c;用Java语言创建的Spring Boot项目中&#xff0c;如何传递数组呢&#xff1f;&#xff1f;-CSDN博客&#xff0c;我们了解到Spring Boot项目中如何传递数组&#xff0c;但是&#xff0c;对于同类型的List集合&#xff0c;我们又该如何…

搜素题目(蓝桥杯 C++ 代码+注解)

目录 题目一&#xff08;小朋友崇拜圈&#xff09;&#xff1a; 代码&#xff1a; 题目二&#xff08;穿越雷区&#xff09;&#xff1a; 代码&#xff1a; 题目三&#xff08;分考场&#xff09;&#xff1a; 代码&#xff1a; 题目四&#xff08;受伤的皇后&#xff09…

蓝桥ACM培训-队列

前言&#xff1a; 第三天的练习&#xff0c;今天主要与队列queue有关。 正文&#xff1a; Problem:A 周末舞会-队列&#xff1a; #include <bits/stdc.h> using namespace std; int m,n,k,tmp1,tmp2; queue<int>q1,q2; int main() {cin>>m>>n>>…

飞天使-学以致用-devops知识点2-安装sonarqube

文章目录 安装sonarqube查看暴露出去的端口 生成服务token创建webhook服务创建项目 安装sonarqube apiVersion: apps/v1 kind: Deployment metadata:name: postgres-sonarnamespace: kube-devops spec:replicas: 1selector:matchLabels:app: postgres-sonartemplate:metadata:…

SQL-Labs靶场“29-31”关通关教程

君衍. 一、二十九关 基于错误的WAF单引号注入1、源码分析2、HTTP参数污染3、联合查询注入4、updatexml报错注入 二、三十关 基于错误的WAF双引号注入1、源码分析2、联合查询注入3、updatexml报错注入 三、三十一关 基于错误的WAF双引号括号注入1、源码分析2、联合查询注入3、up…

个人项目介绍2:地球卫星篇

项目需求&#xff1a; 在项目中显示三维地球及主要城市标注&#xff0c;接收服务端发来的实施卫星数据&#xff0c;显示卫星姿态角&#xff0c;陀螺角&#xff0c;飞轮等数据&#xff1b;可自定义模拟产生更多卫星轨迹&#xff1b;可模拟显示卫星躲避陨石动画&#xff1b;可展…

内含资料下载丨黄东旭:2024 现代应用开发关键趋势——降低成本、简化架构

作为一名工程师和创业者&#xff0c;创办 PingCAP 是我进入创新世界的一次深潜。这段旅程既有令人振奋的发现&#xff0c;也充满令人生畏的不确定性。作为这次探险之旅见证的 TiDB &#xff0c;现在已在全球服务超过 3000 家企业&#xff0c;其中有已经实现了商业成功的大公司&…

Canvas笔记03:Canvas元素功能、属性、获取、原理等一文讲透

hello&#xff0c;我是贝格前端工场&#xff0c;最近在学习canvas&#xff0c;分享一些canvas的一些知识点笔记&#xff0c;本期分享canvas元素的知识&#xff0c;欢迎老铁们一同学习&#xff0c;欢迎关注&#xff0c;如有前端项目可以私信贝格。 Canvas元素是HTML5中的一个重…

(二)逻辑回归与交叉熵--九五小庞

什么是逻辑回归 线性回归预测的是一个连续值&#xff0c;逻辑回归给出的“是”和“否”的回答 Singmoid sigmoid函数是一个概率分布函数&#xff0c;给定某个输入&#xff0c;它将输出为一个概率值 逻辑回归损失函数 平方差所惩罚的是与损失为同一数量级的情形&#xff0…

设计模式(十四)中介者模式

请直接看原文: 原文链接:设计模式&#xff08;十四&#xff09;中介者模式_设计模式之中介模式-CSDN博客 -------------------------------------------------------------------------------------------------------------------------------- 前言 写了很多篇设计模式的…
最新文章