\(\mathscr{Description}\)

  Link.

  求 \(S\subseteq\{1,2,\dots,n\}\),使得 \(\prod_{i\in S}i\) 是完全平方数,并最大化 \(|S|\)。

  \(n\le10^6\)。

\(\mathscr{Solution}\)

  爆搜打出 \(20\) 以内的表,发现 \(|S|\approx n\)。先研究偶数 \(n=2k\):

\[\begin{aligned}
\prod_{i=1}^{2k} i! &= \left( \prod_{i=1}^k i! \right)^2 \prod_{i=1}^k 2i\\
&= \left( \prod_{i=1}^k i! \right)^2 2^k k!.
\end{aligned}
\]

那么若 \(2^kk!\) 是完全平方数,有 \(|S|=n\);否则若 \(2^k\) 是完全平方数,有 \(|S|=n-1\),删去 \(k!\) 即可;否则至少有 \(|S|=n-2\),只需要删去 \(2!\) 和 \(k!\)。继而,对于奇数 \(n=2k+1\),答案至少为 \(n-3\)。

  所以,我们只需要判断 \(|S|\) 能否取 \(n,n-1,n-2\)。这里有个 trick:异或哈希。对于每个素数 \(p\),独立随机生成 hash 值 \(h(p)\),并定义 \(h(ab)=h(a)\oplus h(b)\),这样就能对每个数建立 hash,若两数 \(x,y\) 的唯一分解中指数奇偶性完全一致,就应有 \(h(x)=h(y)\)。利用这个 trick,求出所有 \(h(i!)\) 后顶多拿 unordered map 判一判就能完成 \(S\) 的取值判断了。复杂度为 \(\mathcal O(n)\)(假定 std::unordered_map 为 \(\mathcal O(1)\) 操作)。

\(\mathscr{Code}\)​

/*+Rainybunny+*/

#include <bits/stdc++.h>

#define rep(i, l, r) for (int i = l, rep##i = r; i <= rep##i; ++i)
#define per(i, r, l) for (int i = r, per##i = l; i >= per##i; --i) typedef unsigned long long ULL; const int MAXN = 1e6;
int n, pn, pr[MAXN + 5];
bool npr[MAXN + 5];
ULL hnum[MAXN + 5], hfac[MAXN + 5];
std::unordered_map<ULL, int> buc; inline void init() {
std::mt19937_64 emt(time(0) ^ 20120712);
rep (i, 2, n) {
if (!npr[i]) hnum[pr[++pn] = i] = emt();
for (int j = 1, t; j <= pn && (t = i * pr[j]) <= n; ++j) {
npr[t] = true, hnum[t] = hnum[i] ^ hnum[pr[j]];
if (!(i % pr[j])) break;
}
}
rep (i, 1, n) hfac[i] = hfac[i - 1] ^ hnum[i];
} int main() {
scanf("%d", &n), init(); ULL h = 0;
rep (i, 1, n) h ^= hfac[i]; if (!h) {
printf("%d\n", n);
rep (i, 1, n) printf("%d%c", i, i < n ? ' ' : '\n');
return 0;
} rep (i, 1, n) if (h == hfac[i]) {
printf("%d\n", n - 1);
rep (j, 1, n) if (i != j) printf("%d ", j);
return putchar('\n'), 0;
} rep (i, 1, n) buc[hfac[i]] = i;
rep (i, 1, n) if (buc.count(h ^ hfac[i])) {
printf("%d\n", n - 2); int tmp = buc[h ^ hfac[i]];
rep (j, 1, n) if (j != i && j != tmp) printf("%d ", j);
return putchar('\n'), 0;
} printf("%d\n", n - 3);
rep (i, 1, n - 1) if (i != 2 && i != n >> 1) printf("%d ", i);
return putchar('\n'), 0;
}

Solution -「CF 1622F」Quadratic Set的更多相关文章

  1. Solution -「CF 1342E」Placing Rooks

    \(\mathcal{Description}\)   Link.   在一个 \(n\times n\) 的国际象棋棋盘上摆 \(n\) 个车,求满足: 所有格子都可以被攻击到. 恰好存在 \(k\ ...

  2. Solution -「CF 923F」Public Service

    \(\mathscr{Description}\)   Link.   给定两棵含 \(n\) 个结点的树 \(T_1=(V_1,E_1),T_2=(V_2,E_2)\),求一个双射 \(\varph ...

  3. Solution -「CF 923E」Perpetual Subtraction

    \(\mathcal{Description}\)   Link.   有一个整数 \(x\in[0,n]\),初始时以 \(p_i\) 的概率取值 \(i\).进行 \(m\) 轮变换,每次均匀随机 ...

  4. Solution -「CF 1586F」Defender of Childhood Dreams

    \(\mathcal{Description}\)   Link.   定义有向图 \(G=(V,E)\),\(|V|=n\),\(\lang u,v\rang \in E \Leftrightarr ...

  5. Solution -「CF 1237E」Balanced Binary Search Trees

    \(\mathcal{Description}\)   Link.   定义棵点权为 \(1\sim n\) 的二叉搜索树 \(T\) 是 好树,当且仅当: 除去最深的所有叶子后,\(T\) 是满的: ...

  6. Solution -「CF 623E」Transforming Sequence

    题目 题意简述   link.   有一个 \(n\) 个元素的集合,你需要进行 \(m\) 次操作.每次操作选择集合的一个非空子集,要求该集合不是已选集合的并的子集.求操作的方案数,对 \(10^9 ...

  7. Solution -「CF 1023F」Mobile Phone Network

    \(\mathcal{Description}\)   Link.   有一个 \(n\) 个结点的图,并给定 \(m_1\) 条无向带权黑边,\(m_2\) 条无向无权白边.你需要为每条白边指定边权 ...

  8. Solution -「CF 599E」Sandy and Nuts

    \(\mathcal{Description}\)   Link.   指定一棵大小为 \(n\),以 \(1\) 为根的有根树的 \(m\) 对邻接关系与 \(q\) 组 \(\text{LCA}\ ...

  9. Solution -「CF 487E」Tourists

    \(\mathcal{Description}\)   Link.   维护一个 \(n\) 个点 \(m\) 条边的简单无向连通图,点有点权.\(q\) 次操作: 修改单点点权. 询问两点所有可能路 ...

随机推荐

  1. NIO【同步非阻塞io模型】关于 NIO socket 的详细总结【Java客户端+Java服务端 + 业务层】【可以客户端间发消息】

    1.前言 以前使用 websocket来实现双向通信,如今深入了解了 NIO 同步非阻塞io模型 , 优势是 处理效率很高,吞吐量巨大,能很快处理大文件,不仅可以 做 文件io操作, 还可以做sock ...

  2. Solon 开发,一、注入或手动获取配置

    Solon 开发 一.注入或手动获取配置 二.注入或手动获取Bean 三.构建一个Bean的三种方式 四.Bean 扫描的三种方式 五.切面与环绕拦截 六.提取Bean的函数进行定制开发 七.自定义注 ...

  3. 《剑指offer》面试题62. 圆圈中最后剩下的数字

    问题描述 0,1,n-1这n个数字排成一个圆圈,从数字0开始,每次从这个圆圈里删除第m个数字.求出这个圆圈里剩下的最后一个数字. 例如,0.1.2.3.4这5个数字组成一个圆圈,从数字0开始每次删除第 ...

  4. Rancher Fleet使用教程

    官方文档: https://fleet.rancher.io/ https://github.com/rancher/fleet 博客截止日期为:20201204 当前官网版本为v0.3.0,但在实践 ...

  5. Java的八大基本数据类型

    Java的八大基本数据类型 前言 Bit是计算机存储数据的基本单元,bit叫做位,也被称作比特位. Byte意为字节,1Byte=1字节,一字节可以存储八个二进制位的数字, 即为1Byte=8bit. ...

  6. 【小记录】android下opencv的cv::dft()函数,CPU版本与opencl版本的性能相差16倍

            cv::dft  相差15.9倍         cpu版本  单次调用  0.029448 毫秒         opencl版本  单次调用  0.468688  毫秒   差别仅 ...

  7. 如何理解python中的cmp_to_key()函数

    cmp_to_key() 在functools包里的函数,将老式的比较函数(cmp function)转化为关键字函数(key function). 与接受key function的工具一同使用(如 ...

  8. python变量垃圾回收机制的入门使用

    简介: Python是一款高层次的解释性语言:Python对于初学者来说(易于学习)Python有相对较少的关键字,结构简单,和一个明确定义的语法,学习起来更加简单.学习Python的目的就是为了能够 ...

  9. py调用shell

    py调用shell

  10. 分享一个基于 ABP(.NET 5.0) + vue-element-admin 管理后台

    1.前言 分享一个基于ABP(.NET 5.0) + vue-element-admin项目.希望可以降低新手对于ABP框架的学习成本,感兴趣的同学可以下载项目启动运行一下.对于想选型采用ABP框架的 ...