CCF 202012-3 带配额的文件系统

100%

(参考了这里

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const int N=2e6+15;
const ll inf=(ll)(1e18)<<2;
#define pb push_back
#define mp make_pair
struct node{
    int fa;
    map<string, int> ch;//目录下的孩子文件
    int typ;//0 directory 1 file
    ll siz;
    ll LD,LR;//目录配额,后代配额;
    ll D_size,R_size;//实际占用的大小
    node(int typ=0,ll siz=0):typ(typ),siz(siz){
        fa=0;
        ch.clear();
        LD=inf,LR=inf;
        D_size=0,R_size=0;
    }
}d[N];
int rt=0,cnt=0;
vector<pair<int,string> >rbk;
void rollback(){
    for(auto &t:rbk) d[t.first].ch.erase(t.second);
}
bool C(){
    string path="",to="";ll v=0,changesize=0;
    cin>>path;cin>>v;
    int sz=path.size(),x=rt;
    rbk.clear();
    //directory
    for(int i=1;i<sz;++i){
        if(path[i]=='/'){
            if(!d[x].ch[to]){
                d[x].ch[to]=++cnt;
                d[cnt].fa=x;
                rbk.pb(mp(x,to));
            }
            x=d[x].ch[to];
            if(d[x].typ==1) return rollback(),0;
            to.clear();
        }
        else to+=path[i];
    }
    //file
    if(d[x].ch[to]){
        if(d[d[x].ch[to]].typ==0) return rollback(),0;
        changesize=-d[d[x].ch[to]].siz+v;
    } 
    else{
        changesize=v;
    }
    if(d[x].D_size+changesize>d[x].LD) return rollback(),0;
    for(int y=x;~y;y=d[y].fa){
        if(d[y].R_size+changesize>d[y].LR) return rollback(),0;
    }
    if(!d[x].ch[to]){
        d[x].ch[to]=++cnt;
        d[cnt]=node(1,v);
        d[cnt].fa=x;
    }
    else{
        d[d[x].ch[to]].siz=v;
    }
    d[x].D_size+=changesize;
    for(int y=x;~y;y=d[y].fa) d[y].R_size+=changesize;
    return 1;
}
bool R(){
    string path,to;
    cin>>path;int sz=path.size(),x=rt;
    for(int i=1;i<sz;++i){
        if(path[i]=='/'){
            if(!d[x].ch[to])  return 1;
            x=d[x].ch[to];
            if(d[x].typ==1) return 1;
            to.clear();
        }
        else to+=path[i];
    }
    int t=d[x].ch[to];
    if(!t) return 1;
    ll delsiz=0;
    if(d[t].typ==1){
        d[x].D_size-=(delsiz=d[t].siz);
        d[x].ch.erase(to);
        d[t]=node();
    }
    else{
        delsiz=d[t].R_size;
        d[x].ch.erase(to);
        d[t]=node();
    }
    for(int y=x;~y;y=d[y].fa) d[y].R_size-=delsiz;
    return 1;
}
bool Q(){
    string path="",to="";ll ld=0,lr=0;
    cin>>path;cin>>ld>>lr;
    if(ld==0) ld=inf;
    if(lr==0) lr=inf;
    int sz=path.size(),x=rt;
    for(int i=1;i<sz;++i){
        if(path[i]=='/'){
            if(!d[x].ch[to])  return 0;
            x=d[x].ch[to];
            if(d[x].typ==1) return 0;
            to.clear();
        }
        else to+=path[i];
    }
    int Qnode=rt;
    if(to==""){
        Qnode=rt;
    }
    else{
        if(!d[x].ch[to]) return 0;
        else Qnode=d[x].ch[to];
    }
    if(d[Qnode].typ == 1) return 0;
    if(ld<d[Qnode].D_size||lr<d[Qnode].R_size) return 0;
    d[Qnode].LD=ld,d[Qnode].LR=lr;
    return 1;
}
void print(bool f){puts(f?"Y":"N");}
int main(){
    int n;char opt[4];
    d[rt].fa=-1;
    cin>>n;
    for(int i=0;i<n;++i){
        scanf("%s",opt);
        if(opt[0]=='C') print(C());else
            if(opt[0]=='R') print(R());else
                if(opt[0]=='Q') print(Q());
    }
    return 0;
}

 

posted @ 2021-03-07 12:11  神犇(shenben)  阅读(672)  评论(0编辑  收藏  举报