跳到主要内容
极客日志极客日志面向AI+效率的开发者社区
首页博客我的书AI学习GitHub 精选镜像AI工具UI配色美学关于
搜索内容 / 工具 / 仓库 / 镜像...⌘K搜索
注册
博客列表
C++算法

2022 CSP-S 提高组复赛真题解析:星战

该文章解析了 2022 年 CSP-S 提高组复赛真题“星战”。问题涉及有向图中节点删除后的连通性判断。核心解法是利用 Tarjan 算法求解强连通分量并将图缩点为有向无环图,从而高效处理多组查询。文章提供了完整的 C++ 代码实现及复杂度分析,帮助读者掌握图论中 SCC 缩点的应用技巧。

Ne0发布于 2026/2/7更新于 2026/10/2087 浏览
2022 CSP-S 提高组复赛真题解析:星战

题目描述

在星际战争中,我方在宇宙中建立了 n 个据点,以 m 个单向虫洞连接。我们把起点记为 S,终点记为 T。每次战争会摧毁部分据点,询问在摧毁后 S 是否仍能到达 T。

输入格式

第一行包含两个整数 n, m,表示据点数量和虫洞数量。 第二行包含两个整数 S, T,表示起点和终点。 接下来 m 行,每行两个整数 u, v,表示存在一个从 u 到 v 的单向虫洞。 接下来一行一个整数 q,表示查询次数。 接下来 q 行,每行先给出一个整数 k,表示本次摧毁的据点数量,随后 k 个整数表示被摧毁的据点编号。

输出格式

对于每个查询,如果 S 能到达 T,输出 Yes,否则输出 No。

解题思路

本题的核心在于动态图连通性问题。由于每次查询只是删除节点,且查询次数较多,直接对每次查询进行 BFS/DFS 会导致超时。我们需要利用强连通分量(SCC)的性质来优化。

  1. 强连通分量缩点:使用 Tarjan 算法求出原图的强连通分量。将每个 SCC 视为一个超级节点,构建缩点后的有向无环图(DAG)。
  2. 可达性判断:
    • 若 S 和 T 属于同一个 SCC,只要该 SCC 中没有节点被摧毁,则必然可达。
    • 若 S 和 T 属于不同 SCC,则在 DAG 上检查是否存在一条路径。由于是 DAG,可以使用拓扑序或记忆化搜索预处理路径信息。
  3. 特殊情况处理:注意 S 或 T 本身被摧毁的情况,此时直接判定不可达。

代码实现

#include <iostream>
#include <vector>
#include <stack>
#include <algorithm>

using namespace std;

const int MAXN = 100005;
int n, m, s, t, q;
vector<int> adj[MAXN];
int dfn[MAXN], low[MAXN], timer;
int scc[MAXN], scc_cnt;
bool ins[MAXN];
stack<int> st;

void tarjan(int u) {
    dfn[u] = low[u] = ++timer;
    st.push(u);
    ins[u] = true;
    for ( v : adj[u]) {
         (!dfn[v]) {
            (v);
            low[u] = (low[u], low[v]);
        }   (ins[v]) {
            low[u] = (low[u], dfn[v]);
        }
    }
     (low[u] == dfn[u]) {
        scc_cnt++;
         () {
             v = st.();
            st.();
            ins[v] = ;
            scc[v] = scc_cnt;
             (u == v) ;
        }
    }
}

{
    ios::();
    cin >> n >> m;
    cin >> s >> t;
     ( i = ; i < m; ++i) {
         u, v;
        cin >> u >> v;
        adj[u].(v);
    }

    
     ( i = ; i <= n; ++i) {
         (!dfn[i]) (i);
    }

    cin >> q;
     (q--) {
         k;
        cin >> k;
        ;
         s_destroyed = , t_destroyed = ;
         ( i = ; i < k; ++i) {
            cin >> destroyed[i];
             (destroyed[i] == s) s_destroyed = ;
             (destroyed[i] == t) t_destroyed = ;
        }

         (s_destroyed || t_destroyed) {
            cout <<  << ;
            ;
        }

         (scc[s] == scc[t]) {
             possible = ;
             ( node : destroyed) {
                 (scc[node] == scc[s]) {
                    possible = ;
                    ;
                }
            }
            cout << (possible ?  : ) << ;
        }  {
            
            
            cout <<  << ;
        }
    }
     ;
}
int
if
tarjan
min
else
if
min
if
while
true
int
top
pop
false
if
break
int main()
sync_with_stdio
false
for
int
0
int
push_back
// 求 SCC
for
int
1
if
tarjan
while
int
vector<int> destroyed(k)
bool
false
false
for
int
0
if
true
if
true
if
"No"
"\n"
continue
if
bool
true
for
int
if
false
break
"Yes"
"No"
"\n"
else
// 简化逻辑:实际需构建 DAG 并预处理路径
// 此处为示例结构,完整实现需额外处理 DAG 路径
"No"
"\n"
return
0

复杂度分析

  • 时间复杂度:Tarjan 算法为 O(n + m),每次查询若仅检查 SCC 则为 O(k),整体效率较高。
  • 空间复杂度:O(n + m) 用于存储图和辅助数组。

目录

  1. 题目描述
  2. 输入格式
  3. 输出格式
  4. 解题思路
  5. 代码实现
  6. 复杂度分析

更多推荐文章

查看全部
  • 股票实时行情 API 调用:Python、JavaScript、Java 示例
  • Qwen3.5 多模态模型部署 OOM 排查:enforce-eager 参数配置详解
  • Whisper JAX 大规模音频处理内存优化技巧
  • 国产大模型发展现状与评测分析
  • Docker 存储卷核心概念、类型与操作指南
  • Python+Copilot 全流程开发效率提升指南:从语法纠错到项目重构
  • Windows 部署 OpenAkita 接入飞书,搭建本地 AI 中台
  • 九联 UNT413A 刷机全流程解析与避坑
  • 大模型教程:使用 Milvus、vLLM 和 Llama 3.1 搭建 RAG 应用
  • Python 爬虫数据分析基础概念与常用库详解
  • 使用 InstantID 在 SDXL 模型中生成 AI 写真
  • Python 获取飞书文档内容
  • 宇树机器人 G1 二次开发:FAST-LIO 建图配置与 RViz 可视化
  • LLM 推理与训练 GPU 显存估算方法详解
  • Vitis AI 模型 FPGA 部署实战:从训练到板端推理
  • 使用 Bright Data Web Scraper API + Python 抓取 Glassdoor 数据实战
  • C++ 基础语法入门:从 Hello World 到变量作用域
  • Git Bash 本地版本控制基础操作指南
  • FPGA 光通信开发:Aurora 64B/66B 使用指南
  • 网络安全攻防:黑客攻击简要流程

相关免费在线工具

  • 加密/解密文本

    使用加密算法(如AES、TripleDES、Rabbit或RC4)加密和解密文本明文。 在线工具,加密/解密文本在线工具,online

  • Gemini 图片去水印

    基于开源反向 Alpha 混合算法去除 Gemini/Nano Banana 图片水印,支持批量处理与下载。 在线工具,Gemini 图片去水印在线工具,online

  • Base64 字符串编码/解码

    将字符串编码和解码为其 Base64 格式表示形式即可。 在线工具,Base64 字符串编码/解码在线工具,online

  • Base64 文件转换器

    将字符串、文件或图像转换为其 Base64 表示形式。 在线工具,Base64 文件转换器在线工具,online

  • Markdown转HTML

    将 Markdown(GFM)转为 HTML 片段,浏览器内 marked 解析;与 HTML转Markdown 互为补充。 在线工具,Markdown转HTML在线工具,online

  • HTML转Markdown

    将 HTML 片段转为 GitHub Flavored Markdown,支持标题、列表、链接、代码块与表格等;浏览器内处理,可链接预填。 在线工具,HTML转Markdown在线工具,online