π§© AtCoder Beginner Contest 379
π§© AtCoder Beginner Contest 379
# Info & Summary
- Date:
2024-11-09
- Completion Status: A β / B β / C β / D β / E β / F β / G β
- Problem Type:
Problem | Type(s) | Data Structure / Algo | π₯ Key Insight / Mark |
---|---|---|---|
C | Math | Constructive | π§ |
D | Simulation | Simulation | π§ |
E | Math | Column Addition | π§ π οΈ |
F | Math | Fenwick tree | π |
G | DP | DP | π |
Details
Emoji | Label | Meaning |
---|---|---|
β | Important | Problem is strategically useful or has reusable patterns |
π₯ | Must master | Classic problem or technique that appears often and is worth mastering |
β οΈ | Reattempt | You attempted but failed; worth reviewing and solving again |
π§ | New to me | Introduced a new idea, technique, or pattern you hadnβt seen before |
π οΈ | Template | You built or improved a code template from solving this problem |
π | Too hard now | Beyond current ability to understand/solve; revisit after more practice |
π A - Cyclic

#include <bits/stdc++.h>
using namespace std;
int main()
{
ios::sync_with_stdio(false);
cin.tie(0);
string s;
cin >> s;
cout << s[1] << s[2] << s[0] << ' ' << s[2] << s[0] << s[1] << endl;
return 0;
}
π B - Strawberries

#include <bits/stdc++.h>
using namespace std;
int main()
{
ios::sync_with_stdio(false);
cin.tie(nullptr);
int N, K;
string S;
cin >> N >> K >> S;
int ans = 0;
int cnt = 0;
for (auto c : S)
{
if (c == 'X')
{
cnt = 0;
} else {
cnt += 1;
if (cnt == K)
{
ans += 1;
cnt = 0;
}
}
}
cout << ans << endl;
return 0;
}
π C - Sowing Stones

Tips
Condition that every cell can end up having one stone:
- First, is necessary
- Then the necessary and sufficient condition is that cells have a total of or more stones
Checking the condition for all is a bit difficult because can be up to , but there are only indices such that the total number of stones in cells changes, namely indices , so it is sufficient to scan only
How to find the minimum number of operations required?
Since a stone can only move right (i.e., from smaller index to larger index), every time you move a stone from to , it costs
So, for each stone:
Hence:
Thus, the minimum number of operations is:
- : the ideal total sum of final positions (1-based, each position gets 1 stone)
- : the total sum of initial positions of all stones
#include <bits/stdc++.h>
using namespace std;
int main()
{
ios::sync_with_stdio(false);
cin.tie(nullptr);
long long N, M;
cin >> N >> M;
vector<pair<int, long long>> A(M);
for (int i = 0; i < M; i++)
{
cin >> A[i].first;
}
for (int i = 0; i < M; i++)
{
cin >> A[i].second;
}
sort(A.begin(), A.end());
long long sum = 0, idx = 0;
for (auto p : A)
{
if (sum < p.first - 1)
{
cout << -1 << endl;
return 0;
}
sum += p.second;
idx += p.second * p.first;
}
cout << (sum != N ? -1 : N * (N + 1) / 2 - idx) << endl;
return 0;
}
π D - Home Garden

Type 1: Plant a seed
a.push_back(-t);
Because this plant's actual height when we evaluate later will be:
- At planting time:
This trick avoids needing to store separate timestamps
#include <bits/stdc++.h>
using namespace std;
int main()
{
ios::sync_with_stdio(false);
cin.tie(nullptr);
int Q;
cin >> Q;
// a: Stores offsets for each planted plant
vector<long long> a;
// s: Index pointer to the first unharvested plant
int s = 0;
// t: Cumulative total of growth (from all type-2 operations)
long long t = 0;
for (int i = 0; i < Q; i++)
{
int o;
cin >> o;
if (o == 1)
{
a.push_back(-t);
}
else if (o == 2)
{
int T;
cin >> T;
t += T;
}
else
{
int H;
cin >> H;
int ans = 0;
// compute actual height as a[s] + t
while (s < a.size() && a[s] + t >= H)
{
s++;
ans++;
}
cout << ans << endl;
}
}
return 0;
}
π E - Sum of All Substrings

Base-10 column addition
First, consider how the answer can be represented when is small
When , the answer is as follows:
More generally, for , the answer is:
This means: every digit appears in multiple substrings, and its contribution is weighted by its place in the string and the number of substrings that include it
#include <bits/stdc++.h>
using namespace std;
int main()
{
ios::sync_with_stdio(false);
cin.tie(nullptr);
int N;
cin >> N;
string S;
cin >> S;
// Build A_i
vector<long long> a(N);
long long sum = 0;
for (int i = 0; i < N; i++)
{
// \sum_{j = 1}^{i} j \times S_j
sum += (S[i] - '0') * (i + 1);
// reverses the index to line up with 10^i
a[N - 1 - i] = sum;
}
// Perform base-10 column addition (manual carry propagation)
// This manually handles large digit values by propagating carries like elementary addition
for (int i = 0; i < a.size(); i++)
{
if (a[i] >= 10)
{
if (i + 1 >= a.size())
{
a.resize(i + 2); // make space for carry
}
a[i + 1] += a[i] / 10; // carry to next digit
a[i] %= 10; // keep remainder in this digit
}
}
// Digits are stored with least significant digit first, so we reverse them before printing
reverse(a.begin(), a.end());
for (auto x : a)
{
cout << x;
}
cout << endl;
return 0;
}
π F - Buildings 2

Warning
Hard Problems to Tackle Later
// TODO
π G - Count Grid 3-coloring

Warning
Hard Problems to Tackle Later
// TODO