10月10日,xju新生赛https://ac.nowcoder.com/acm/contest/8021
异或
题目描述:
给定一个长度为n初始全为0的数列ai,下标从1开始。定义操作模k异或v为对所有满足i ≡0(modk) 的下标i,将异或上整数v(即令ai=ai⊕v)。
给出q次操作,每次操作之后输出序列的异或和,并且在操作结束之后输出整个序列。
序列的异或和为a1⊕a2⊕…⊕an
解题要点:
异或定义,异或性质(任意个0异或结果为0,0与某数x异或结果为x,偶数个相同的数异或结果为0)。
//ljs学长代码,码源:https://ac.nowcoder.com/acm/contest/view-submission?submissionId=45201992 #include <bits/stdc++.h> #define ios std::ios::sync_with_stdio(false) #define rep(i, a, n) for (int i = a; i <= n; i++) #define per(i, n, a) for (int i = n; i >= a; i--) #define int long long #define ll long long using namespace std; const ll INF(0x3f3f3f3f3f3f3f3fll); const int inf(0x3f3f3f3f); const int N = 1e6 + 10; int a[N], cnt[N];//a[]存放操作结束后的序列;cnt[]存放原数列中有过操作的项 signed main(){ int n, m, res = 0, ma = 0; cin >> n >> m; for(int i=1; i<=m; i++) { int k, v; cin >> k >> v; int x = (n / k);//判断这n个数字里面有几个需要异或 //两个相同的数字异或为0 if (x % 2) res ^= v;//如果是奇数,那么表示最后还剩下一个 cout << res << ' '; if (k > n) continue;//就表示没有需要异或的,上面的x也就是0 cnt[k] ^= v; ma = max(ma, k);//找到最大的k } for(int i=1; i<=ma; i++) { if (!cnt[i])//若cnt[i]为零,说明原数列第i项未经过操作。此处结束本次循环,执行下一次循环 continue; for (int j = i; j <= n; j += i) { a[j] ^= cnt[i]; } } for(int i=1; i<=n; i++) cout << a[i] << " "; cout << ' '; return 0; }
最近的两个点 (排序后分治合并。板子题,以后再看)
题目描述:
给定三维空间上n个点,每个点都有xi,yi,zi三个坐标值.找出其中的一对点的距离,使得在这n个点的所有点对中,该距离为所有点对中最小的.
//码源:https://blog.csdn.net/qq_41286356/article/details/109005591 #include<bits/stdc++.h> using namespace std; const int N=1e5+10; struct node { double x,y,z; }; bool cmpx(node a,node b) { return a.x<b.x; } bool cmpy(node a,node b) { return a.y<b.y; } node p[N], a[N]; int cnt, n; double dis(node a, node b) { return sqrt((a.x-b.x)*(a.x-b.x)+(a.y-b.y)*(a.y-b.y)+(a.z-b.z)*(a.z-b.z)); } double run(int l, int r) { if(l + 1 == r) return dis(p[l], p[r]); if(l + 2 == r){ return min({dis(p[l],p[l+1]), dis(p[l],p[l+2]), dis(p[l+1],p[l+2])}); } int mid = l + r >> 1; double ans = min(run(l, mid), run(mid+1, r)); cnt = 0; for(int i=l;i<=r;++i){ if(p[i].x >= p[mid].x - ans && p[i].x <= p[mid].x + ans){ a[cnt++] = p[i]; } } sort(a, a+cnt, cmpy); for(int i=0;i<cnt;++i){ for(int j=i+1;j<cnt;++j){ if(a[j].y-a[i].y > ans) break; ans = min(ans, dis(a[i], a[j])); } } return ans; } int main() { scanf("%d", &n); for(int i=0;i<n;++i){ scanf("%lf%lf%lf", &p[i].x,&p[i].y,&p[i].z); } sort(p, p+n, cmpx); printf("%.3f ", run(0, n - 1)); }