1. 程式人生 > 其它 >Educational Codeforces Round 106 (Rated for Div. 2) C. Minimum Grid Path

Educational Codeforces Round 106 (Rated for Div. 2) C. Minimum Grid Path

題目連結

  • 思路:

只能往上和右走(直角座標系y軸關於x軸對稱下來,然後x和y調換下位置),所以總共走的路長只有2*n

由於每個a[i]代表的是在下一次轉向前每走一步的花費,所以可以考慮貪心

只要找到最小的每步代價,將前面的都置為一步,剩下的用最小代價走完,所得的總代價即為答案

列舉每一個a[i],對於前面的代價和i個單次步長,直接使用字首和即可,然後迴圈中每次分別維護x軸和y軸上的最小值計算即可

  • 程式碼:

#include <bits/stdc++.h>
#define ll long long

using namespace std;

typedef pair<ll, ll> PII;

const int N = 1e5 + 10, mod = 998244353;

int n;
ll a[N], sum[N];

void solve()
{
    cin >> n;
    for (int i = 1; i <= n; ++ i)
    {
        cin >> a[i];
        sum[i] = sum[i - 1] + a[i];
    }

    ll ans = a[1] * n + a[2] * n;
    ll tempj = a[1], tempo = a[2];
    for (int i = 3; i <= n; i ++)
    {
        if(i % 2) tempj = min(tempj, a[i]);
        else tempo = min(tempo, a[i]);
        ll re = 2 * n - i;
        ll t1 = re / 2, t2 = re - t1; //由於tempj是第一步的,所以奇數時它要比另一方向上多走一次/步,所以直接除即可
        ans = min(ans, sum[i] + t1 * tempj + t2 * tempo);
    }
    cout << ans << endl;
}

int main()
{
    ios::sync_with_stdio(0);
    int T;
    cin >> T;
    while(T --)
    {
        solve();
    }
    return 0;
}