1.?小紅的簽到題
現在小紅希望你寫出一個長度為 nnn 的、使用了下劃線命名法命名的變量。為了顯出特征,請保證該變量至少由兩個單詞組成。
輸入描述:
輸入一個正整數 n(3≦n≦100),代表需要構造的變量長度。
輸出描述:
輸出一個長度為 n?的字符串,代表你所構造的使用了下劃線命名法命名的變量。 如果存在多個解決方案,您可以輸出任意一個,系統會自動判定是否正確。注意,自測運行功能可能因此返回錯誤結果,請自行檢查答案正確性。
示例1
輸入
11
輸出
kato_megumi
解題思路:根據長度n構造答案
#include<bits/stdc++.h>
using namespace std;
int main(){int n; cin>>n;cout<<"f_"<<string(n-2,'f')<<endl;
}
?2.?小紅的模擬題
給定一個?n?行 m?列的網格,我們使用 (i,j) 表示網格中從上往下數第 i 行和從左往右數第 j?列的格子。小紅現在位于 (1,1),準備前往 (n,m)。
然而,不是所有的格子都是可以通行的,有且恰有一個格子是陷阱格,一旦小紅踏入陷阱格,就會直接去逝。保證這個陷阱格不會出現在 (1,1)和 (n,m)。
小紅每一步只能向右或者向下前進。請你幫小紅規劃一條行動路線,使得她可以順利到達?(n,m)。
行動路線為一個僅由字符 ‘D’、‘S’ 構成的字符串 s,第 i個字符代表小紅第 i 次行動的方向。記第 iii 次行動前小紅位于 (x,y),則:
,若si?=‘D’,則小紅向右移動一格即抵達 (x,y+1);
,若si?=‘S’,則小紅向下移動一格即抵達(x+1,y)。
解題思路:由于陷阱只有一個, 從(1,1) 到 (n,m), 特殊情況一種是往右n-1步, 往下走m-1步, 另一種是往下走m-1步, 往右走n-1步, 陷阱最多只會出現在上述兩條路徑中的一條之中, 所以依次探測即可?
#include <bits/stdc++.h>
using namespace std;
int main() {int n, m;cin >> n >> m;vector<string> grid(n);for(int i=0;i<n;i++) cin>>grid[i];bool f1=true;for(int i=1;i<n;i++){if(grid[i][0]=='#') f1=false;}for(int j=1;j<m;j++){if(grid[n-1][j]=='#') f1=false;}if(f1){for(int i=1;i<n;i++) cout<<'S';for(int j=1;j<m;j++) cout<<'D';return 0;}bool f2=true;for(int j=1;j<m;j++){if(grid[0][j]=='#') f2=false;}for(int i=1;i<n;i++){if(grid[i][m-1]=='#') f2=false;}if(f2){for(int i=1;i<m;i++) cout<<'D';for(int i=1;i<n;i++) cout<<'S';return 0;}return 0;
}
?3.小紅的方神題
題目描述
對于數組 a,我們定義它的退化狀態為:取每個相鄰兩數之差的絕對值構成的新數組。換句話說,退化后的 a?數組是一個長度為len(a)?1 的數組,其第 i?個元素為 ∣ai??ai+1?∣。
?希望小紅構造一個長度為 n 的排列,使得其連續進行n?1 次退化后,最終生成的一個整數恰好等于 n?2。你能幫幫小紅嗎?如果不存在這樣的排列,直接輸出 ?1 即可。
長度為 n?的排列是由 1,2,…,n 這 n個整數、按任意順序組成的數組(每個整數均恰好出現一次)。例如,{2,3,1,5,4} 是一個長度為 5 的排列,而 {1,2,2} 和 {1,3,4} 都不是排列,因為前者存在重復元素,后者包含了超出范圍的數。
解題思路: 1/2都不行, n>=3時候, 構造[1,n,n?1,…,2]? 相鄰差后為:[|1-n|, 1,1,....], 再退化一次為, n-2, 滿足題意。
#include <bits/stdc++.h>
using namespace std;
int main(){int n; cin>>n;if(n<=2) { cout<<-1<<endl; return 0; }cout<<1;for(int i=n;i>=2;i--){cout<<" "<<i;}cout<<endl;return 0;
}
4.?小紅的數學題?
題目描述
小紅拿到了一個正整數 k,她希望你找到兩個正整數 p,q,滿足 p+q=k,且方程 x^2?px+q=0 存在兩個正整數解。特別地,如果不存在這樣的 p,q,請輸出 ?1。
解題思路:設方程的兩個根為x1和x2,
x1+x2=p,
x1*x2=q,
x1+x2+x1*x2=k,
x1+x2+x1*x2+1=k+1?
(x1+1)*(x2+1)=k+1
所以, 我們可以將k+1, 分解成兩個>=2的數的乘積(a,b)
x1+1=a, x2+1=b,?
p=a+b-2, q=(a-1)*(b-1)
#include <bits/stdc++.h>
using namespace std;
int main(){long long k;cin >> k;long long t = k + 1;long long A = -1, B = -1;for (long long d = 2; d * d <= t; d++) {if (t % d == 0) {A = d;B = t / d;break;}}if (A == -1){cout << -1 << endl;}else{long long p = (A + B - 2);long long q = (A - 1) * (B - 1);cout << p << " " << q << endl;}return 0;
}
?5.?小紅的ds題
小紅希望你構造一棵層數為 n?的二叉樹,其第 i?層恰好有 ai? 個節點。你能幫幫她嗎?
一棵樹被稱為二叉樹,當且僅當其滿足:
,?每個節點要么沒有父節點連接(此時該節點被稱為根節點)、要么被 1?個父節點連接(此時該節點被稱為父節點的子節點;?每個節點連接的子節點數量要么為 0(此時該節點被稱為葉子節點)、要么小于等于 2(此時該節點被稱為分支節點)。
#include <bits/stdc++.h>
using namespace std;
int main() {int n; cin >> n;vector<int> nums(n); int total = 0;for (int i = 0; i < n; i++) {cin >> nums[i];total += nums[i];}vector<int> son_cnt(total, 0); vector<vector<int>> tmp(total); int start = 0;int pt = nums[0]; for (int i = 1; i < n; i++) {int new_start = pt;while (nums[i]--) {while (son_cnt[start] == 2) {start++;}son_cnt[start]++;tmp[start].push_back(pt);pt++;}start = new_start;}cout << 1 << endl; for (int i = 0; i < total; i++) {if (tmp[i].empty()) {cout << "-1 -1"<<endl;} else if (tmp[i].size() == 1) {cout << "-1 " << tmp[i][0] + 1 <<endl;} else {cout << tmp[i][0] + 1 << ' ' << tmp[i][1] + 1 << endl;}}return 0;
}
6.小紅的小苯題?
題目描述
小苯希望小紅構造一個 n?行 m?列的矩陣,滿足:
,?每一行所有元素的異或和、每一列所有元素的異或和,這 n+m 個數恰好構成一個長度為 n+m的排列。
?矩陣中每個元素的值在 0 到 10^9 之間。
你能幫幫小紅嗎?
長度為 n?的排列是由 1,2,…,n 這 n 個整數、按任意順序組成的數組(每個整數均恰好出現一次)。例如,{2,3,1,5,4} 是一個長度為 5?的排列,而 {1,2,2}?和 都不是排列,因為前者存在重復元素,后者包含了超出范圍的數。
解題思路(詳細思考過程):
n行m列
設每一行所有元素的異或和分別為R1, R2, R3, .... ,Rn
設每一列所有元素的異或和分別為C1, C2, C3,....Cm
這些 n+m 個行異或和和列異或和合在一起,正好是 1,2,…,n+m 的一個排列
那我們應該怎么構造呢?
我們可以直接讓行異或和Ri=i(第 1 行異或和是 1,第 2 行是 2,……,第?n?行是?n)
列異或和 Cj?=n+j(即第 1 列異或和是 n+1,第 2 列是 n+2,……,第 m 列是 n+m)
這個{Ri}U{Cj} ={1,2,3,4,....,n+m}
所有的行異或和R1 xor R2 xor R3 xor...xor?Rn應該等于所有列異或和C1 xor C2 xor C3 xor ...xor Cm (因為矩陣的總異或和可以從行或列兩個方向計算)
因此, (R1 xor R2 xor R3 xor...xor?Rn) xor (C1 xor C2 xor C3 xor ...xor Cm) =0
=> 1 xor 2 xor 3 xor ...xor (n+m)=0
所以,?
只有 1 到 n+m 的異或和為 0 時,才能構造出這樣的矩陣
具體構造:
為了簡化問題,?
除了最后一列和最后一行,其他位置都填 0
填最后一列(行異或和)
對于前 n?1 行,讓它們的最后一列等于行異或和 a[i][m]=Ri =i
(第i行的異或和就是0 xor 0 xor ...i=i)
填最后一行(列異或和)
對于前 m?1 行,讓它們的最后一列等于列異或和 a[n][j]=Ci =n+j
(第j列的異或和就是0 xor 0 xor ...(n+j)=n+j)
最后填A[n][m]這個位置,?A[n][m]需要同時滿足:
1. 第n行的異或和是Rn=n, 2. 第m列的異或和是 Cm=n+m
第?n?行的異或和是 C1 xor C2 xor C3 xor ,,, xor Cm-1 xor t =n
?(n+1) xor (n+2) xor ... xor (n+m-1) xor t=n
所以, t1=n xor (n+1) xor (n+2) xor ... xor (n+m-1)?
同理,?
第m列的異或和是 R1 xor R2 xor R3 xor ... xor Rn-1 xor t
1 xor 2 xor ... xor (n-1) xor t= n+m
所以, t2=(n+m) xor 1 xor 2 xor ... xor (n-1)?
注:t1==t2
最后, 簡單說一下代碼中各部分的含義
solve函數:計算前k個數的異或和是否等于0
a數組:初始化待構造的數組
然后分別填最后一列的前n-1行, 最后一行的前m-1列
最后填充右下角的元素,?
按t2進行計算
最后輸出構造的a數組即可
性質:1⊕2⊕?⊕(n+m)=0。
構造方法:
前?n?1n?1?行的最后一列填?i+1i+1(保證行異或和)
前?m?1m?1?列的最后一行填?n+j+1n+j+1(保證列異或和)
右下角填?T=(n+m)⊕(1⊕2⊕?⊕(n?1))T=(n+m)⊕(1⊕2⊕?⊕(n?1))。
輸出:直接打印矩陣
#include <bits/stdc++.h>
using namespace std;
int solve(int k) {int ans=0;for(int i=0;i<=k;i++){ans^=i;}return ans;
}
int main(){int n, m;cin >> n >> m;if (solve(n + m) != 0) {cout << -1 << endl;return 0;}vector<vector<long long>> a(n, vector<long long>(m, 0));for (int i = 0; i < n - 1; i++) {a[i][m-1] = i + 1; }for (int j = 0; j < m - 1; j++) {a[n-1][j] = n + (j + 1); }long long x = 0;for (int i = 1; i <= n - 1; i++) x ^= i;long long t = (n + m) ^ x; a[n-1][m-1] = t;for (int i = 0; i < n; i++) {for (int j = 0; j < m; j++) {cout << a[i][j] << (j+1<m? ' ' : '\n');}}return 0;
}
感謝大家的點贊和關注,你們的支持是我創作的動力!(有疑問可以發布到評論區)
吐槽:感覺比京津冀某藍某橋某杯略難吧(想了解可以看我往期題解)