제출 #895204

#제출 시각아이디문제언어결과실행 시간메모리
895204Tuanlinh123Two Currencies (JOI23_currencies)C++17
40 / 100
713 ms95568 KiB
#include<bits/stdc++.h>
#define ll long long
#define pll pair<ll, ll>
#define pb push_back
#define mp make_pair
#define fi first
#define se second
#define ld long double
using namespace std;

struct BIT 
{
    ll n;
    vector <ll> bit;

    BIT (ll n): n(n)
    {
        bit.assign(n+1, 0);
    }

    void update(ll l, ll r, ll val)
    {
        for (; l<=n; l+=l&(-l))
            bit[l]+=val;
        for (++r; r<=n; r+=r&(-r))
            bit[r]-=val;
    }

    ll query(ll i)
    {
        ll ans=0;
        for (; i; i-=i&(-i))
            ans+=bit[i];
        return ans;
    }
};

const ll maxn=100005;
vector <pll> euler;
pll edge[maxn], sp[20][maxn]; 
vector <ll> A[maxn], C[maxn], Q[maxn];
ll Time, tin[maxn], tout[maxn], lca[maxn], pa[maxn], dis[maxn];
ll p[maxn], c[maxn], s[maxn], t[maxn], x[maxn], y[maxn], l[maxn], r[maxn], ans[maxn];

void dfs(ll u)
{
    tin[u]=++Time;
    lca[u]=euler.size()+1;
    euler.pb({lca[u], u});
    for (ll v:A[u])
        if (v!=pa[u])
        {
            pa[v]=u, dfs(v);
            euler.pb({lca[u], u});
        }
    tout[u]=Time;
}

void getdis(ll u)
{
    for (ll v:A[u])
        if (v!=pa[u])
            dis[v]+=dis[u], getdis(v);
}

void init_sparse()
{
    ll n=euler.size();
    for (ll i=0; i<n; i++)
        sp[0][i+1]=euler[i];
    for (ll i=1; i<20; i++)
        for (ll j=1; j+(1<<i)<=n+1; j++)
            sp[i][j]=min(sp[i-1][j], sp[i-1][j+(1<<i-1)]);
}

ll LCA(ll u, ll v)
{
    ll l=lca[u], r=lca[v];
    if (l>r) swap(l, r);
    ll j=__lg(r-l+1);
    return min(sp[j][l], sp[j][r-(1<<j)+1]).se;
}

int main()
{
    ios_base::sync_with_stdio(0);
    cin.tie(0); cout.tie(0);
    ll n, m, q; cin >> n >> m >> q;
    for (ll i=1; i<n; i++)
    {
        ll u, v; cin >> u >> v;
        A[u].pb(v); A[v].pb(u);
        edge[i]={u, v};
    }
    vector <pll> numc;
    dfs(1); init_sparse();
    for (ll i=1; i<n; i++)
        if (edge[i].se==pa[edge[i].fi])
            swap(edge[i].fi, edge[i].se);
    for (ll i=1; i<=m; i++)
    {
        cin >> p[i] >> c[i];
        numc.pb({c[i], edge[p[i]].se});
        dis[edge[p[i]].se]++;
    }
    sort(numc.begin(), numc.end());
    getdis(1);
    for (ll i=1; i<=q; i++)
    {
        cin >> s[i] >> t[i] >> x[i] >> y[i];
        l[i]=0, r[i]=m, ans[i]=-1;
    }
    for (ll z=0; z<20; z++)
    {
        for (ll i=1; i<=q; i++)
            Q[(l[i]+r[i]+1)/2].pb(i);
        BIT A(n), B(n);
        for (ll i=0; i<=m; i++)
        {
            if (i)
            {
                ll P=numc[i-1].se;
                A.update(tin[P], tout[P], numc[i-1].fi);
                B.update(tin[P], tout[P], 1);
            }
            for (ll idx:Q[i])
            {
                ll u=s[idx], v=t[idx], X=x[idx], Y=y[idx], lca=LCA(u, v);
                ll sum=A.query(tin[u])+A.query(tin[v])-A.query(tin[lca])*2;
                ll cnt=B.query(tin[u])+B.query(tin[v])-B.query(tin[lca])*2;
                ll cnt2=dis[u]+dis[v]-dis[lca]*2;
                if (sum<=Y)
                {
                    if (cnt2-cnt<=X) ans[idx]=max(ans[idx], X-(cnt2-cnt));
                    l[idx]=i;
                }
                else r[idx]=i-1;
            }
            Q[i].clear();
        }
    }
    for (ll i=1; i<=q; i++)
        cout << ans[i] << "\n";
}

컴파일 시 표준 에러 (stderr) 메시지

currencies.cpp: In function 'void init_sparse()':
currencies.cpp:73:53: warning: suggest parentheses around '-' inside '<<' [-Wparentheses]
   73 |             sp[i][j]=min(sp[i-1][j], sp[i-1][j+(1<<i-1)]);
      |                                                    ~^~
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...