T1、矩阵乘法

题目链接

给定一个 \(n \times n \ (n \leq 500)\) 的矩阵 \((a_{i,j} \leq 10 ^ 9)\),\(q \ (q \leq 6 \times 10 ^ 5)\) 组询问,每次询问一个子矩阵的第 \(k\) 大元素 (保证存在)。

\(Sol\):

整体二分主席树,注意常数因子带来的影响;
全场只有我一个常数怪 \(95\) 分。

时间复杂度 \(O(q \log_2^2 n)\)。

\(Source\):

//#pragma GCC optimize(2)
#include <cstdio>
#include <cstring>
#include <algorithm>
inline int in() {int x = 0; char c = getchar(); bool f = 0;while (c < '0' || c > '9')f |= c == '-', c = getchar();while (c >= '0' && c <= '9')x = (x << 1) + (x << 3) + (c ^ 48), c = getchar();return f ? -x : x;
}
template<typename T>inline void chk_min(T &_, T __) { _ = _ < __ ? _ : __; }
template<typename T>inline void chk_max(T &_, T __) { _ = _ > __ ? _ : __; }const int N = 505, Q = 60005;struct info {int id, x1, y1, x2, y2, k;
} b[N * N + Q];
int n, m, q, id[N * N + Q], tmp1[N * N + Q], tmp2[N * N + Q], pos[N * N], res[Q];
int nn, mp[N * N];struct persistable_segment_tree {int sum[N * N * 11], c[N * N * 11][2], rt[N * N], tot;void clear() {tot = 0;}int new_node() {++tot;sum[tot] = c[tot][0] = c[tot][1] = 0;return tot;}void modify(int pos, int tl, int tr, int pre, int &p) {p = new_node(), sum[p] = sum[pre];++sum[p];if (tl == tr)return ;int mid = (tl + tr) >> 1;if (mid >= pos) {c[p][1] = c[pre][1];modify(pos, tl, mid, c[pre][0], c[p][0]);} else {c[p][0] = c[pre][0];modify(pos, mid + 1, tr, c[pre][1], c[p][1]);}}int query(int l, int r, int tl, int tr, int pre, int p) {if (l <= tl && tr <= r)return sum[p] - sum[pre];int mid = (tl + tr) >> 1;if (mid < l)return query(l, r, mid + 1, tr, c[pre][1], c[p][1]);if (mid >= r)return query(l, r, tl, mid, c[pre][0], c[p][0]);return query(l, r, tl, mid, c[pre][0], c[p][0]) +query(l, r, mid + 1, tr, c[pre][1], c[p][1]);}
} T;void binary_search(int l, int r, int s, int t) {if (l > r || s > t)return ;if (l == r) {for (int i = s; i <= t; ++i)if (b[id[i]].id)res[b[id[i]].id] = mp[l];return ;}int mid = (l + r) >> 1, p1 = 0, p2 = 0, tot = 0;T.clear();for (int i = s; i <= t; ++i) {if (!b[id[i]].id) {if (b[id[i]].k <= mp[mid]) {T.modify(b[id[i]].y1, 1, n, T.rt[tot], T.rt[tot + 1]);tmp1[++p1] = id[i];pos[++tot] = b[id[i]].x1;} else {tmp2[++p2] = id[i];}} else {int x, y, w;x = std::lower_bound(pos + 1, pos + 1 + tot, b[id[i]].x1) - pos;y = std::upper_bound(pos + 1, pos + 1 + tot, b[id[i]].x2) - pos - 1;w = T.query(b[id[i]].y1, b[id[i]].y2, 1, n, T.rt[x - 1], T.rt[y]);if (w >= b[id[i]].k) {tmp1[++p1] = id[i];} else {b[id[i]].k -= w;tmp2[++p2] = id[i];}}}for (int i = 1; i <= p1; ++i)id[s + i - 1] = tmp1[i];for (int i = 1; i <= p2; ++i)id[s + p1 + i - 1] = tmp2[i];binary_search(l, mid, s, s + p1 - 1);binary_search(mid + 1, r, s + p1, t);
}int main() {//freopen("in", "r", stdin);n = in(), q = in();for (int i = 1; i <= n; ++i)for (int j = 1; j <= n; ++j) {b[++m] = (info){0, i, j, 0, 0, in()};mp[++nn] = b[m].k;}for (int i = 1; i <= q; ++i)b[++m] = (info){i, in(), in(), in(), in(), in()};for (int i = 1; i <= m; ++i)id[i] = i;std::sort(mp + 1, mp + 1 + nn);nn = std::unique(mp + 1, mp + 1 + nn) - mp - 1;binary_search(0, nn, 1, m);for (int i = 1; i <= q; ++i)printf("%d\n", res[i]);return 0;
}

T2、Tree

题目链接

给定一张 \(n \ (n \leq 100)\) 个点 \(m \ (m \leq 2000)\) 条边的无相连通图,有边权 \(C_i \ (0 \leq C_i \leq 100)\),求最小标准差生成树。

\(Sol\):

可以将答案看做一个关于平均数的函数:
\[ f(x) = \sqrt{ \frac{\sum (C_i - x) ^ 2}{n - 1} } \]
枚举 \(x\),将边权设为 \(C_i - x\),求最小生成树,再按最小生成树的真实平均数更新答案。
具体证明我不会,大概是对于每个 \(x\) 得到的真实平均值一定是与 \(x\) 相邻的。

时间复杂度 \(O(\)能跑多少跑多少\()\)。

\(Source\):

#include <cstdio>
#include <algorithm>
#include <cmath>
typedef double db;
int in() {int x = 0; char c = getchar(); bool f = 0;while (c < '0' || c > '9')f |= c == '-', c = getchar();while (c >= '0' && c <= '9')x = (x << 1) + (x << 3) + (c ^ 48), c = getchar();return f ? -x : x;
}
template<typename T>inline void chk_min(T &_, T __) { _ = _ < __ ? _ : __; }
template<typename T>inline void chk_max(T &_, T __) { _ = _ > __ ? _ : __; }const int N = 105, M = 2005;
const db eps = 1e-5;db res, now;
int n, m;
int fa[N];
struct edge {int u, v, w;inline bool operator < (const edge &b) const {return (this->w - now) * (this->w - now) < (b.w - now) * (b.w - now);}
} e[M];int get_fa(int u) {return fa[u] == u ? u : fa[u] = get_fa(fa[u]);
}void calc() {res = 1 << 30;for (now = 100; now > 0; now -= 0.25) {std::sort(e + 1, e + 1 + m);int now_edge = 0, _sum = 0, sum = 0;for (int i = 1; i <= n; ++i)fa[i] = i;for (int i = 1; i <= m && now_edge < n - 1; ++i) {int fx = get_fa(e[i].u), fy = get_fa(e[i].v);if (fx == fy)continue;fa[fx] = fy;++now_edge;_sum += e[i].w * e[i].w, sum += e[i].w;}db tmp = sqrt(((db)(n - 1) * _sum - sum * sum) / (n - 1) / (n - 1));if (res - tmp > eps)res = tmp;}
}int main() {//freopen("in", "r", stdin);n = in(), m = in();if (n == 1) {puts("0.0000");return 0;}for (int i = 1; i <= m; ++i)e[i] = (edge){in(), in(), in()};calc();printf("%.4lf\n", res);return 0;
}

T3、Points and Segments

题目链接

数轴上给定 \(n \ (n \leq 10 ^ 5)\) 条线段,每条线段为红色或蓝色,给出一种颜色方案,使得数轴上所有点被不同颜色覆盖的次数差绝对值不超过 \(1\)。

\(Sol\):

可以把原数轴上的点看作线段,点被颜色覆盖可以看作线段被覆盖;
题目中\([l,r]\) 线段就可以当作新图中 \([l,r + 1]\) 中所有线段被覆盖。

问题转化为所有线段被覆盖的绝对值不超过 \(1\);
\(l\) 向 \(r + 1\) 连无向边,\(l\) 到 \(r + 1\) 即为染成蓝色,否则染成红色;
这样如果该图有欧拉回路 (所有点都是偶点),则两色覆盖次数都相等;
若有奇点,那么奇点个数一定是偶数 (一条线段有两个端点),则从左到右第 \(2i\) 和 \(2i + 1\) 个奇点连边;
该图一定有欧拉回路,所有被覆盖的次数都相等;
因为新加的边之间一定不会相交,所以把他们删掉后每个点只会少覆盖一次。

时间复杂度 \(O(n)\)。

\(Source\):

#include <cstdio>
#include <cstring>
#include <algorithm>
inline int in() {int x = 0; char c = getchar(); bool f = 0;while (c < '0' || c > '9')f |= c == '-', c = getchar();while (c >= '0' && c <= '9')x = (x << 1) + (x << 3) + (c ^ 48), c = getchar();return f ? -x : x;
}
template<typename T>inline void chk_min(T &_, T __) { _ = _ < __ ? _ : __; }
template<typename T>inline void chk_max(T &_, T __) { _ = _ > __ ? _ : __; }const int N = 1e5 + 5;struct node {int l, r;
} a[N];
struct edge {int next, to;
} e[N << 2];
int ecnt = 1, head[N << 1];
int n, nn, mp[N << 1], res[N], deg[N << 1];
bool vis[N << 1], used[N << 1];inline void jb(const int u, const int v) {e[++ecnt] = (edge){head[u], v}, head[u] = ecnt;e[++ecnt] = (edge){head[v], u}, head[v] = ecnt;++deg[u], ++deg[v];
}void prep() {for (int i = 1; i <= n; ++i) {a[i] = (node){in(), in()};mp[++nn] = a[i].l, mp[++nn] = a[i].r;}std::sort(mp + 1, mp + 1 + nn);nn = std::unique(mp + 1, mp + 1 + nn) - mp - 1;for (int i = 1; i <= n; ++i) {a[i].l = std::lower_bound(mp + 1, mp + 1 + nn, a[i].l) - mp;a[i].r = std::lower_bound(mp + 1, mp + 1 + nn, a[i].r) - mp;jb(a[i].l, a[i].r);}int last = 0;for (int i = 1; i <= nn; ++i)if (deg[i] & 1) {if (!last)last  = i;elsejb(last, i), last = 0;}
}void dfs(const int u) {used[u] = 1;for (int i = head[u]; i; i = e[i].next) {if (!vis[i >> 1]) {vis[i >> 1] = 1;dfs(e[i].to);if (u > e[i].to)res[i >> 1] = 1;elseres[i >> 1] = 0;}}
}void work() {for (int i = 1; i <= nn; ++i)if (!used[i])dfs(i);
}int main() {//freopen("in", "r", stdin);n = in();prep();work();for (int i = 1; i <= n; ++i)printf("%d ", res[i]);puts("");return 0;
}

转载于:https://www.cnblogs.com/15owzLy1-yiylcy/p/11402365.html

「2019纪中集训Day23」解题报告相关推荐

  1. 「2019纪中集训Day7」解题报告

    T1.小L的数列 给一个数列 \(\{f_i\}\): \[ f_i = \prod_{j = 1}^{j \leq k} f_{i - j}^{b_j}, \ (i > k) \] 现在给定数 ...

  2. 「2019纪中集训Day12」解题报告

    T1.迷宫 一个 $ n \times m  (n \leq 5, m \leq 10 ^ 5) $ 的矩阵,\(0\) 表示格子不能走,\(1\) 表示格子可以走,只能向上.下.右三个方向走.有 $ ...

  3. 2019纪中集训总结

    其实用一句话总结的话,那么就是: We still have a long way to go. 来到纪中,才知道全国还有这么多优秀的OI神犇,才知道自己不过是井下之蛙,才知道自己之前的幼自满的幼稚. ...

  4. 2019寒假纪中集训总结学期总结(流水账)

    学期总结 这学期上了初三,学校的初.高中校区对调,我们的班主任也由一个生物老师换成了一个化学老师. 之前的班主任比较年轻,跟我们这群学生有这很好的感情,亦师亦友,陪伴我们度过了几乎没有中考压力的初一. ...

  5. 用typescript完成倒计时_「2019 JSConf.Hawaii - Brie.Bunge」大规模应用 TypeScript

    特别说明 这是一个由 simviso 团队对 JSConf.Hawaii 中关于 TypeScript 相关话题进行翻译的文档,内容并非直译,其中有一些是笔者自身的思考.分享者为 Brie.Bunge ...

  6. 「2019 JSConf.Hawaii - Brie.Bunge」大规模应用 TypeScript

    特别说明 这是一个由 simviso 团队对 JSConf.Hawaii 中关于 TypeScript 相关话题进行翻译的文档,内容并非直译,其中有一些是笔者自身的思考.分享者为 Brie.Bunge ...

  7. 倒计时 3 天!「2019 嵌入式智能国际大会」全日程大公开!

    立即抢购:https://t.csdnimg.cn/otBk 还有3天,大伙期待的「2019嵌入式智能国际大会」正式开幕了! 2019年12月6日-7日,我们在深圳市人才研修院见! 大会以" ...

  8. 8.3折特惠票仅剩3天!「2019 嵌入式智能国际大会」全日程大公开!

    8.3折特惠票仅剩3天 立即抢购:https://t.csdnimg.cn/otBk 还有5天,大伙期待的「2019嵌入式智能国际大会」正式开幕了! 2019年12月6日-7日,我们在深圳市人才研修院 ...

  9. 学习 launch-editor 源码整体架构,探究 vue-devtools「在编辑器中打开组件」功能实现原理...

    1. 前言 你好,我是若川[1],微信搜索「若川视野」关注我,专注前端技术分享,一个愿景是帮助5年内前端开阔视野走向前列的公众号.欢迎加我微信ruochuan12,长期交流学习. 这是学习源码整体架构 ...

最新文章

  1. 集成ACEGI 进行权限控制
  2. 在离线环境中使用.NET Core
  3. html九图拼图游戏代码,HTML5拼图游戏
  4. 北师大名教授通过趣味数学与幽默教你学数学思维
  5. Android开发笔记(一百三十三)导航视图NavigationView
  6. Python菜鸟入门:day10模块介绍
  7. Day01 - 打开Linux大门
  8. 女神节福利来了!(自动驾驶/三维重建/SLAM/点云/标定/深度估计/3D检测)
  9. windows ping 端口测试
  10. 解决IDM浏览器插件强制更新后无法继续使用的问题
  11. 51单片机学习 基础知识总结
  12. ESP32 485光照度
  13. U3D教程多摄像机协同运行
  14. 蜂窝六边形的六边形消除高分秘籍
  15. 打开一个浏览器跳转到2345浏览器主页 这里以Google为例 亲测已解决。
  16. 巧用SEO技术,速提自然流量
  17. FreeRtos软件定时器复习
  18. (以Windows 7 引导的)Windows 和Ubuntu双系统安装
  19. android 记事本ppt,基于Android记事本软件设计与实现.ppt
  20. Unraid下虚拟DSM7.1,并开启相册人脸识别

热门文章

  1. 使用unity粒子系统制作烟花
  2. img图片加载错误时显示默认图片
  3. 2015出现神曲空挡期,玖月奇迹接棒筷子兄弟?
  4. 2022安全员-B证操作证考试题库及答案
  5. 文字怎么转语音?这些方法值得收藏
  6. android模拟器如何正确安装HAXM加速器
  7. 怎么将mov格式的视频转换成MP4?
  8. iOS 设置自定义间距的文字下划线
  9. 给孩子简单快乐的童年
  10. iOS 开发项目之 QQ 音乐