T1: 音乐盒

本题难度简单,\(T\) 可能很大,这样就需要转圈循环并会导致超时,可以先将 \(T\) 对所有歌曲的总时间取模,再去遍历一遍歌曲即可找到答案

代码实现
#include <bits/stdc++.h>
#define rep(i, n) for (int i = 0; i < (n); ++i)
 
using namespace std;
using ll = long long;
 
int main() {
	int n; 
	cin >> n;
	
	vector<ll> t(n);
	rep(i, n) cin >> t[i];
	
	ll T;
	cin >> T;
	
	ll s = 0; 
	rep(i, n) {
	    s += t[i];
	    if (s > T) { // 注意 s 可能会爆 long long,所以需要特判
	        cout << i+1 << '\n';
	        return 0;
	    }
	}
	T %= s;
	
	if (T == 0) {
	    cout << n << '\n';
	    return 0;
	}
	
	rep(i, n) {
	    if (T <= t[i]) {
	        cout << i+1 << '\n';
	        return 0;
	    }
	    T -= t[i];
	}
	
	return 0;
}

T2:整数拆分

本题难度中等,双重循环枚举 \(x\)\(y\) 进行判断即可拿到 \(60\) 分,对 \(f(x, y) = (x+1)(y+1) - 1\) 变形可知 \(y\) 一定是 \(10^k-1\)\(x\) 可以是任意值,因此计算 \(y\) 的个数,然后通过乘法原理计算答案

\( f(x, y) = x \cdot y^k + y = (x+1)(y+1) - 1 \)
\( \Rightarrow x \cdot 10^k + y = xy + x + y \)
\( \Rightarrow x \cdot 10^k = xy+x \)
\( \Rightarrow 10^k = y+1 \)
\( \Rightarrow y = 10^k-1 \)

代码实现
#include <bits/stdc++.h>
#define rep(i, n) for (int i = 0; i < (n); ++i)

using namespace std;
using ll = long long;

int main() {
    int m, n;
    cin >> m >> n;
    
    ll cnt = 0, y = 9;
    while (y <= n) {
        cnt++;
        y = y*10+9;
    }
    
    ll ans = cnt*m;
    cout << ans << '\n';
	
	return 0;
}

T3:龙虎斗(二)

本题难度中等,考察枚举思想与前缀和技巧。枚举分界点 \(i\),能够发现当分界点从 \(i-1\) 移动到 \(i\) 时,左边总和增加 \(a_1 + a_2 + \cdots + a_{i-1}\),右边总和减少 \(a_i + a_{i+1} + \cdots + a_n\),计算这部分区间和可以使用前缀和技巧。

代码实现
#include <bits/stdc++.h>
#define rep(i, n) for (int i = 0; i < (n); ++i)

using namespace std;
using ll = long long;

int main() {
    int n;
    cin >> n;
    
    vector<ll> c(n);
    rep(i, n) cin >> c[i];
    
    vector<ll> s(n);
    s[0] = c[0];
    for (int i = 1; i < n; ++i) s[i] = s[i-1]+c[i];
    
    ll ans = 9e18, sumL = 0, sumR = 0;
    for (int i = 1; i < n; ++i) {
        sumR += i*c[i];
    }
    ans = min(ans, sumR);
    for (int i = 1; i < n; ++i) {
        sumL += s[i];
        sumR -= s[n-1]-s[i];
        ans = min(ans, abs(sumL-sumR));
    }
    
    cout << ans << '\n';
    
    return 0;
}