【图论经典题目讲解】CF786B - Legacy 一道线段树优化建图的经典题目

2024-02-17 06:36

本文主要是介绍【图论经典题目讲解】CF786B - Legacy 一道线段树优化建图的经典题目,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

C F 786 B − L e g a c y \mathrm{CF786B - Legacy} CF786BLegacy

D e s c r i p t i o n \mathrm{Description} Description

给定 1 1 1 n n n 个点的有向图,初始没有边,接下来有 q q q 次操作,形式如下:

  • 1 u v w 表示从 u u u v v v 连接 1 1 1 条长度为 w w w 的有向边
  • 2 u l r w 表示从 u u u i i i i ∈ [ l , r ] i\in [l,r] i[l,r])连接 1 1 1 条长度为 w w w 的有向边
  • 3 u l r w 表示从 i i i i ∈ [ l , r ] i\in [l,r] i[l,r])向 u u u 连接 1 1 1 条长度为 w w w 的有向边

输出从 S S S 点到 i i i 点( i ∈ [ 1 , n ] i\in [1,n] i[1,n])的最短路长度。

S o l u t i o n \mathrm{Solution} Solution

观察可知,最多会建立 1 0 5 × 1 0 5 = 1 0 10 10^5\times 10^5 = 10^{10} 105×105=1010 条边,故必定超时。

此时,需要使用 线段树优化建图,这里展开简单说一下:

对于 1 1 1 棵存储点为 1 ∼ 4 1\sim 4 14 的线段树,形式如下:

image-20240215212043652

如果当前为 2 2 2 操作,且为 1 ∼ 3 1\sim 3 13 每个点连向 4 4 4,权值为 10 10 10,操作如下所示:

image-20240215212212466

即,将区间 1 ∼ 2 1\sim 2 12 3 ∼ 3 3\sim 3 33 连向 4 4 4 即可,不过此时发现,图中为有向图,而现在是无向图所以我们要对于图中的每一条边标记方向和权值(这里线段树就是一张图,叶子节点就是我们的 1 ∼ n 1\sim n 1n 节点)

image-20240215212641895

其中,为何线段树上的边方向都为向父亲节点?那是因为 1 1 1 2 2 2 号点只有这样才能顺着边走到 4 4 4 号节点,对于为何权值设为 0 0 0,因为这是 1 1 1 条虚边(不存在的),不能对最短路做出任何贡献。

不过,上文是区间连节点,当是节点连区间的时候(操作 3 3 3)边都是正好反着的,所以再建 1 1 1 棵线段树即可(不过没必要真的去再建 1 1 1 棵,具体见代码)

C o d e Code Code

#include <bits/stdc++.h>
#define int long longusing namespace std;typedef pair<int, int> PII;
typedef long long LL;const int SIZE = 4e6 + 10, SIZE2 = 1e6 + 10;int N, Q, S;
int h[SIZE2], e[SIZE], ne[SIZE], w[SIZE], idx;
int Id[2], Dist[SIZE2], Vis[SIZE2];
struct Segment
{int l, r;int L, R;
}Tree[SIZE2 << 2];void add(int a, int b, int c)
{e[idx] = b, ne[idx] = h[a], w[idx] = c, h[a] = idx ++;
}int Build(int l, int r, int Sd, int k)
{if (l == r){Tree[l] = {l, l};return l;}int P = ++ Id[k];Tree[P] = {l, r};int mid = l + r >> 1;Tree[P].L = Build(l, mid, Sd, k), Tree[P].R = Build(mid + 1, r, Sd, k);if (!Sd) add(Tree[P].L, P, 0), add(Tree[P].R, P, 0);else add(P, Tree[P].L, 0), add(P, Tree[P].R, 0);return P;
}void Add(int u, int l, int r, int p, int w, int Sd)
{if (Tree[u].l >= l && Tree[u].r <= r){if (!Sd) add(u, p, w);else add(p, u, w);return;}int mid = Tree[u].l + Tree[u].r >> 1;if (mid >= l) Add(Tree[u].L, l, r, p, w, Sd);if (mid < r) Add(Tree[u].R, l, r, p, w, Sd);
}void Dijkstra(int S)
{memset(Dist, 0x3f, sizeof Dist);memset(Vis, 0, sizeof Vis);priority_queue<PII, vector<PII>, greater<PII>> Heap;Heap.push({0, S}), Dist[S] = 0;while (Heap.size()){auto Tmp = Heap.top();Heap.pop();int u = Tmp.second;if (Vis[u]) continue;Vis[u] = 1;for (int i = h[u]; ~i; i = ne[i]){int j = e[i];if (Dist[j] > Dist[u] + w[i]){Dist[j] = Dist[u] + w[i];Heap.push({Dist[j], j});}}}
}signed main()
{cin.tie(0);cout.tie(0);ios::sync_with_stdio(0);memset(h, -1, sizeof h);cin >> N >> Q >> S;if (N == 1){cout << 0 << endl;return 0;}Id[0] = N;Build(1, N, 0, 0);Id[1] = Id[0];Build(1, N, 1, 1);while (Q --){int Op, v, u, l, r, w;cin >> Op >> u;if (Op == 1){cin >> v >> w;add(u, v, w);}else if (Op == 2){cin >> l >> r >> w;Add(Id[0] + 1, l, r, u, w, 1);}else{cin >> l >> r >> w;Add(N + 1, l, r, u, w, 0);}}Dijkstra(S);for (int i = 1; i <= N; i ++)if (Dist[i] >= 1e18) cout << -1 << " ";else cout << Dist[i] << " ";return 0;
}

这篇关于【图论经典题目讲解】CF786B - Legacy 一道线段树优化建图的经典题目的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/716955

相关文章

SQL Server中行转列方法详细讲解

《SQLServer中行转列方法详细讲解》SQL行转列、列转行可以帮助我们更方便地处理数据,生成需要的报表和结果集,:本文主要介绍SQLServer中行转列方法的相关资料,需要的朋友可以参考下... 目录前言一、为什么需要行转列二、行转列的基本概念三、使用PIVOT运算符进行行转列1.创建示例数据表并插入数

C++,C#,Rust,Go,Java,Python,JavaScript的性能对比全面讲解

《C++,C#,Rust,Go,Java,Python,JavaScript的性能对比全面讲解》:本文主要介绍C++,C#,Rust,Go,Java,Python,JavaScript性能对比全面... 目录编程语言性能对比、核心优势与最佳使用场景性能对比表格C++C#RustGoJavapythonjav

Spring Boot基于 JWT 优化 Spring Security 无状态登录实战指南

《SpringBoot基于JWT优化SpringSecurity无状态登录实战指南》本文介绍如何使用JWT优化SpringSecurity实现无状态登录,提高接口安全性,并通过实际操作步骤... 目录Spring Boot 实战:基于 JWT 优化 Spring Security 无状态登录一、先搞懂:为什

Java JAR 启动内存参数配置指南(从基础设置到性能优化)

《JavaJAR启动内存参数配置指南(从基础设置到性能优化)》在启动Java可执行JAR文件时,合理配置JVM内存参数是保障应用稳定性和性能的关键,本文将系统讲解如何通过命令行参数、环境变量等方式... 目录一、核心内存参数详解1.1 堆内存配置1.2 元空间配置(MetASPace)1.3 线程栈配置1.

VS Code中的Python代码格式化插件示例讲解

《VSCode中的Python代码格式化插件示例讲解》在Java开发过程中,代码的规范性和可读性至关重要,一个团队中如果每个开发者的代码风格各异,会给代码的维护、审查和协作带来极大的困难,这篇文章主... 目录前言如何安装与配置使用建议与技巧如何选择总结前言在 VS Code 中,有几款非常出色的 pyt

Java中实现对象的拷贝案例讲解

《Java中实现对象的拷贝案例讲解》Java对象拷贝分为浅拷贝(复制值及引用地址)和深拷贝(递归复制所有引用对象),常用方法包括Object.clone()、序列化及JSON转换,需处理循环引用问题,... 目录对象的拷贝简介浅拷贝和深拷贝浅拷贝深拷贝深拷贝和循环引用总结对象的拷贝简介对象的拷贝,把一个

Docker多阶段镜像构建与缓存利用性能优化实践指南

《Docker多阶段镜像构建与缓存利用性能优化实践指南》这篇文章将从原理层面深入解析Docker多阶段构建与缓存机制,结合实际项目示例,说明如何有效利用构建缓存,组织镜像层次,最大化提升构建速度并减少... 目录一、技术背景与应用场景二、核心原理深入分析三、关键 dockerfile 解读3.1 Docke

从原理到实战解析Java Stream 的并行流性能优化

《从原理到实战解析JavaStream的并行流性能优化》本文给大家介绍JavaStream的并行流性能优化:从原理到实战的全攻略,本文通过实例代码给大家介绍的非常详细,对大家的学习或工作具有一定的... 目录一、并行流的核心原理与适用场景二、性能优化的核心策略1. 合理设置并行度:打破默认阈值2. 避免装箱

Python实战之SEO优化自动化工具开发指南

《Python实战之SEO优化自动化工具开发指南》在数字化营销时代,搜索引擎优化(SEO)已成为网站获取流量的重要手段,本文将带您使用Python开发一套完整的SEO自动化工具,需要的可以了解下... 目录前言项目概述技术栈选择核心模块实现1. 关键词研究模块2. 网站技术seo检测模块3. 内容优化分析模

Java实现复杂查询优化的7个技巧小结

《Java实现复杂查询优化的7个技巧小结》在Java项目中,复杂查询是开发者面临的“硬骨头”,本文将通过7个实战技巧,结合代码示例和性能对比,手把手教你如何让复杂查询变得优雅,大家可以根据需求进行选择... 目录一、复杂查询的痛点:为何你的代码“又臭又长”1.1冗余变量与中间状态1.2重复查询与性能陷阱1.