1 条题解

  • 3
    @ 2025-3-19 12:46:39

    特殊情况:

    • □ -> □:满足限制の二元限制个数 v2 v^2

    (1, 1), (1, 2), ..., (1, v),

    (2, 1), (2, 2), ..., (2, v),

    ......

    (v, 1), (v, 2), ..., (v, v)

    • □ -> □ -> ...(m 条二元限制)-> □:满足限制の二元限制个数 (v2)m (v^2)^m

    • a -> b:不满足限制の二元限制个数 (v1) (v-1)

    (a, 1), (a, 2), ..., (a, b-1), (a, b+1), ..., (a, v)

    满足限制の二元限制个数 v2(v1)=v2v+1 v^2-(v-1) = v^2-v+1

    • a -> □ -> b:不满足限制の二元限制个数 v(v1) v*(v-1)

    (a, □) -> (□, 1), (□, 2), ..., (□, b-1), (□, b+1), ..., (□, v) 1v 1 \le □ \le v

    满足限制の二元限制个数 (v2)2(v2v)=(v2)2v2+v (v^2)^2-(v^2-v) = (v^2)^2-v^2+v

    一般情况:

    • a -> □ -> □ -> ...(m 条二元限制)-> b:不满足限制の二元限制个数 vm1(v1) v^{m-1}*(v-1)

    满足限制の二元限制个数 (v2)mvm1(v1) (v^2)^m-v^{m-1}*(v-1)

    P.S. 本题目略卡常。。。

    #include<cstdio>
    #include<map>
    using namespace std;
    
    int const mod=1e9+7;
    
    long long pow(long long b, int p){
    	long long ans=1;
    	while(p){
    		if(p%2) (ans *= b) %= mod;
    		(b *= b) %= mod;
    		
    		p /= 2;
    	}
    	
    	return ans;
    }
    
    map<int, int> num;
    
    int fuction(){
    	num.clear();
    
    	int n, m;
    	scanf("%d%d", &n, &m);
    	
    	int limit;
    	scanf("%d", &limit);
    	
    	bool flag=0;
    	while(m--){
    		int ix, val;
    		scanf("%d%d", &ix, &val);
    		
    		map<int, int>::iterator it=num.find(ix);
    		
    		if(it!=num.end() && it->second!=val) flag = 1;
    		else num.insert(make_pair(ix, val));
    	}
    	
    	if(flag) return 0;
    	
    	map<int, int>::iterator it=num.begin();
    	long long ans=pow(pow(limit, 2), it->first-1);
    	
    	while(true){
    		int pre=it->first;
            
            if(++it == num.end()) break;
    
            int now=it->first;
    		(ans *= pow(pow(limit, 2), now-pre)-pow(limit, now-pre-1)*(limit-1)%mod+mod) %= mod;
    	}
    
    	(ans *= pow(pow(limit, 2), n-(--it)->first)) %= mod;
    	
    	return ans;
    }
    
    int main(){
        freopen("assign.in", "r", stdin);
        freopen("assign.out", "w", stdout);
    
    	int T;
    	scanf("%d", &T);
    	
    	while(T--){
    		int ans=fuction();
    
    		printf("%d\n", ans);
    	}
    	
        fclose(stdin);
        fclose(stdout);
    
    	return 0;
    }
    

    信息

    ID
    2226
    时间
    1000ms
    内存
    512MiB
    难度
    9
    标签
    递交数
    30
    已通过
    3
    上传者