社区讨论

求解答三个问题

P2396yyy loves Maths VII参与者 3已保存回复 6

讨论操作

快速查看讨论及其快照的属性,并进行相关操作。

当前回复
6 条
当前快照
1 份
快照标识符
@mbvlgywm
此快照首次捕获于
2025/06/14 10:05
9 个月前
此快照最后确认于
2025/11/04 07:12
4 个月前
查看原帖
  1. 代码的时间复杂度是多少?用了 lowbit 优化的时间复杂度还是 O(N2N+NM)\mathcal{O}(N * 2 ^ N + N * M) 吗?如果是,为什么不超时?代码运行的大致次数超过了四个亿……?“常数优化”到底优化在哪使得运行次数小于两个亿?AC 代码连样例 2 都超时……
  2. 开 long long 会爆空间 MLE,但是 ai1e9a_i \le 1e9,三个幸运数字(即 3ai3 * a_i)就会超过 int 范围(3000000000>21474836473000000000 \gt 2147483647),更何况说 nn 个幸运数字……所以为什么不会爆 int 而导致答案错误呢?
  3. 在不考虑时间复杂度的情况下,下面这两份代码实现内容上的区别是什么?为什么一个得十分一个 AC?
这两份代码的 dp 都是一模一样的,不一样的点在于 aia_i,即对判断是否踩在厄运数字上的统计和的方式不同。
CPP
//WA,仅 AC #3
int main(){
	int n, m, S;
	n = read();
	S = (1 << n) - 1;
	for(int i = 1; i <= n; ++i){
		a[i] = read() % Mod;
	} 
	m = read();
	for(int i = 1; i <= m; ++i){
		b[i] = read() % Mod;
	}
	for(int i = 2; i <= S; ++i){
		lg[i] = lg[i >> 1] + 1;
	}
	f[0] = 1;
	for(int i = 1; i <= S; ++i){
		int s = 0, ff = 1;
		for(int j = i; j > 0; j -= lowbit(j)){
			s += a[lg[lowbit(j)] + 1];
		}
		for(int j = 1; j <= m; ++j){
			if(s == b[i]){
				ff = 0;
				break;
			}
		}
		if(ff == 0) continue;;
		for(int j = i; j > 0; j -= lowbit(j)){
			f[i] += f[i ^ lowbit(j)];
			f[i] %= Mod;
		}
	}
	write(f[S]);
	return 0;
} 
CPP
//AC,题解做法
int main(){
	int n, m, S;
	n = read();
	S = (1 << n) - 1;
	for(int i = 1; i <= n; ++i){
		a[1 << i - 1] = read() % Mod;
	} 
	m = read();
	for(int i = 1; i <= m; ++i){
		b[i] = read() % Mod;
	}
	f[0] = 1;
	for(int i = 1; i <= S; ++i){
		a[i] = a[i ^ lowbit(i)] + a[lowbit(i)];
		if(a[i] == b[1] || a[i] == b[2]) continue;
		for(int j = i; j > 0; j -= lowbit(j)){
			f[i] += f[i ^ lowbit(j)];
			f[i] %= Mod;
		}
	}
	write(f[S]);
	return 0;
} 

回复

6 条回复,欢迎继续交流。

正在加载回复...