test 7 3-22 2021省选模拟赛seven

考试复盘

T 1 T1 T1

s u b t a s k 1 : n ≤ 5 subtask1:n\le 5 subtask1:n5,暴搜点的颜色状态以及边的存在状态

对于一条连接相同颜色点的边,可要可不要,不会提供形态变化的贡献, 2 e d g e 2^{edge} 2edge

d p dp dp???

d p [ i ] [ j ] [ 0 / 1 ] dp[i][j][0/1] dp[i][j][0/1]表示前 i i i个点,颜色为白/黑,由前面 j j j个点转移过来?

好像转移不动。。pass

T 2 T2 T2

n ≤ 15 n\le 15 n15??感觉给子任务编号,是不同数据下的算法拼凑而来的呢(〃 ̄︶ ̄)人( ̄︶ ̄〃)

s u b t a s k 1 : m ≤ 20 subtask1:m\le 20 subtask1:m20,直接 2 m 2^m 2m暴搜

竟然空间超限,ε=(・д・`*)ハァ…,哭晕在厕所

s u b t a s k 2 : 1 − 2 subtask2:1-2 subtask2:12之间有唯一的一条简单路径

考虑枚举在这条路径上的 i i i点相遇,则除了这条路径以外的边的方向都无所谓

s u b t a s k 3 : n ≤ 10 → m ≤ 45 subtask3:n\le 10\rightarrow m\le 45 subtask3:n10m45

s u b t a s k 4 : subtask4: subtask4:一般情况

考虑枚举在点 x x x相遇,暴搜 1 − x 1-x 1x每一条路径,在此基础上搜 2 − x 2-x 2x的每一条路径,没被打标记的边可选可不选;

但是这里会出现重复的情况,因为路径并不是唯一的

emmmmmm(▼㉨▼メ)难搞哦(・。・)

T 3 T3 T3

字符匹配非常类似最近做的 F F T FFT FFT题_(:3J∠)

可仔细想想,又不太对劲,pass

猜个小结论:长度是每段只比上一段加一,感觉就是对的

考虑 d p [ i ] [ j ] dp[i][j] dp[i][j],表示串 [ l , r ] [l,r] [l,r]作为首串,最多能接的段数

转移,要枚举位置??比较串, k m p kmp kmp?? h a s h hash hash??,好像时间复杂度有点大诶

算了吧。。。

考后

唯一想说的,对于这场比赛就只有空间超限了,(*゚Д゚)つミ匚___

人生

在这里插入图片描述 n ≤ 2 e 5 n\le 2e5 n2e5


e n d i end_i endi表示以 i i i为结尾的路径条数

如果 e n d j end_j endj是偶数条,连向 i i i后, e n d i end_i endi也只会加上偶数,奇偶性不变

如果 e n d j end_j endj是奇数条,连向 i i i后, e n d i end_i endi会加上奇数,奇偶性变化

注意 e n d i end_i endi要加上 1 1 1,自己到自己的路径

由此得知, e n d i end_i endi奇偶性只跟前面与 i i i连边的点中 e n d j end_j endj是奇数的点的个数有关,与实际点是哪个无关

f [ i ] [ j ] [ k ] [ h ] f[i][j][k][h] f[i][j][k][h]:表示前 i i i个点,有 j j j个白点和 k k k个黑点的 e n d end end是奇数,且前 i i i个点 e n d end end之和的奇偶性为 h h h 0 0 0 1 1 1奇)

对于一个 n n n元集合( n > 1 n>1 n>1),选出一个偶数子集大小或者是一个奇数子集大小的方案数均为 2 n − 1 2^{n-1} 2n1


简单证明一下( ̄▽ ̄)":

n n n为奇数

假设选了 i i i个, i i i为奇数,那么 n − i n-i ni个没有选, n − i n-i ni为偶数

说明每选一种奇数子集大小的方案,就会存在一种偶数子集大小的方案

各自占一半, = 2 n 2 = 2 n − 1 =\frac{2^n}{2}=2^{n-1} =22n=2n1

n n n为偶数

T ( n , 1 ) T(n,1) T(n,1)表示在 n n n个中选奇数个的方案数, T ( n , 0 ) T(n,0) T(n,0)表示在 n n n个中选偶数个的方案数

考虑把 n n n分成前后各一半

Ⅰ设 n / 2 n/2 n/2为奇数

T ( n , 1 ) = T ( n / 2 , 1 ) ∗ T ( n / 2 , 0 ) + T ( n / 2 , 0 ) ∗ T ( n / 2 , 1 ) = 2 ∗ T ( n / 2 , 0 ) ∗ T ( n / 2 , 1 ) T(n,1)=T(n/2,1)*T(n/2,0)+T(n/2,0)*T(n/2,1)=2*T(n/2,0)*T(n/2,1) T(n,1)=T(n/2,1)T(n/2,0)+T(n/2,0)T(n/2,1)=2T(n/2,0)T(n/2,1)

T ( n , 0 ) = T ( n / 2 , 1 ) ∗ T ( n / 2 , 1 ) + T ( n / 2 , 0 ) ∗ T ( n / 2 , 0 ) T(n,0)=T(n/2,1)*T(n/2,1)+T(n/2,0)*T(n/2,0) T(n,0)=T(n/2,1)T(n/2,1)+T(n/2,0)T(n/2,0)

先前证明过当 x x x为奇数时,其选择奇数和偶数的方案数相等

T ( n , 0 ) = T ( n / 2 , 1 ) ∗ T ( n / 2 , 0 ) + T ( n / 2 , 0 ) ∗ T ( n / 2 , 1 ) = 2 ∗ T ( n / 2 , 0 ) ∗ T ( n / 2 , 1 ) T(n,0)=T(n/2,1)*T(n/2,0)+T(n/2,0)*T(n/2,1)=2*T(n/2,0)*T(n/2,1) T(n,0)=T(n/2,1)T(n/2,0)+T(n/2,0)T(n/2,1)=2T(n/2,0)T(n/2,1)

⇒ T ( n , 0 ) = T ( n , 1 ) \Rightarrow T(n,0)=T(n,1) T(n,0)=T(n,1)

Ⅱ设 n / 2 n/2 n/2为偶数

递归 n / 2 n/2 n/2,不停的除以 2 2 2,总有一层是奇数,就变成了Ⅰ

证毕


大力讨论列出转移方程

①点 i + 1 i+1 i+1为白色,且 e n d end end为偶数,总和奇偶性不变
f [ i + 1 ] [ j ] [ k ] [ h ] = f [ i ] [ j ] [ k ] [ h ] ∗ 2 k − 1 ∗ 2 i − k f[i+1][j][k][h]=f[i][j][k][h]*2^{k-1}*2^{i-k} f[i+1][j][k][h]=f[i][j][k][h]2k12ik

2 k − 1 2^{k-1} 2k1:会对 i + 1 i+1 i+1奇偶性造成影响的 k k k个黑色奇数点,从中选择奇数个的方案数, e n d i + 1 end_{i+1} endi+1有这些黑色奇数点带来的奇数贡献,再加上自己到自己本身一条路径,就是偶数了

2 i − k 2^{i-k} 2ik:剩下的点与 i + 1 i+1 i+1可连可不连,不会造成影响

②点 i + 1 i+1 i+1为白色,且 e n d end end为奇数,总和奇偶改变
f [ i + 1 ] [ j + 1 ] [ k ] [ h ⨁ 1 ] = f [ i ] [ j ] [ k ] [ h ] ∗ 2 k − 1 ∗ 2 i − k f[i+1][j+1][k][h\bigoplus1]=f[i][j][k][h]*2^{k-1}*2^{i-k} f[i+1][j+1][k][h1]=f[i][j][k][h]2k12ik

2 k − 1 2^{k-1} 2k1:会对 i + 1 i+1 i+1奇偶性造成影响的 k k k个黑色奇数点,从中选择偶数个的方案数

③点 i + 1 i+1 i+1为黑色,且 e n d end end为偶数,总和奇偶性不变
f [ i + 1 ] [ j ] [ k ] [ h ] = h [ i ] [ j ] [ k ] [ h ] ∗ 2 j − 1 ∗ 2 i − j f[i+1][j][k][h]=h[i][j][k][h]*2^{j-1}*2^{i-j} f[i+1][j][k][h]=h[i][j][k][h]2j12ij

2 j − 1 2^{j-1} 2j1:会对 i + 1 i+1 i+1奇偶性造成影响的 j j j个白色奇数点,从中选择奇数个的方案数

④点 i + 1 i+1 i+1为黑色,且 e n d end end为奇数,总和奇偶改变
f [ i + 1 ] [ j ] [ k + 1 ] [ h ⨁ 1 ] = f [ i ] [ j ] [ k ] [ h ] ∗ 2 j − 1 ∗ 2 i − j f[i+1][j][k+1][h\bigoplus 1]=f[i][j][k][h]*2^{j-1}*2^{i-j} f[i+1][j][k+1][h1]=f[i][j][k][h]2j12ij

2 j − 1 2^{j-1} 2j1:会对 i + 1 i+1 i+1奇偶性造成影响的 j j j个白色奇数点,从中选择偶数个的方案数

如果点 i + 1 i+1 i+1被钦定为黑色,则没有①②的转移;白色则没有③④的转移

观察到每个转移方程中后面两个 2 2 2的幂乘积与 j , k j,k j,k无关,都为 2 i − 1 2^{i-1} 2i1
j , k j,k j,k 0 0 0时,从中选偶数个为 2 i 2^i 2i,选奇数个为 0 0 0

于是,不再需要 j , k j,k j,k的实际值了

f [ i ] [ 0 / 1 ] [ 0 / 1 ] [ h ] f[i][0/1][0/1][h] f[i][0/1][0/1][h],表示前 i i i个点, e n d end end和的奇偶为 h h h,是否有 e n d end end为奇数的白/黑点

#include <cstdio>
#define int long long
#define mod 998244353
#define maxn 200005
int f[maxn][2][2][2];
int mi[maxn], c[maxn];
int n;

signed main() {
	scanf( "%lld", &n );
	for( int i = 1;i <= n;i ++ ) scanf( "%lld", &c[i] );
	mi[0] = 1;
	for( int i = 1;i <= n;i ++ ) mi[i] = ( mi[i - 1] << 1 ) % mod;
	f[0][0][0][0] = 1;
	for( int i = 0;i < n;i ++ )
	for( int j = 0;j <= 1;j ++ )
	for( int k = 0;k <= 1;k ++ )
	for( int h = 0;h <= 1;h ++ ) {
		if( ! f[i][j][k][h] ) continue;
		if( c[i + 1] != 1 ) {
			f[i + 1][j][k][h] = ( f[i + 1][j][k][h] + f[i][j][k][h] * ( k ? mi[i - 1] : 0 ) % mod ) % mod;
			f[i + 1][j | 1][k][h ^ 1] = ( f[i + 1][j | 1][k][h ^ 1] + f[i][j][k][h] * ( k ? mi[i - 1] : mi[i] ) % mod ) % mod;
		}
		if( c[i + 1] != 0 ) {
			f[i + 1][j][k][h] = ( f[i + 1][j][k][h] + f[i][j][k][h] * ( j ? mi[i - 1] : 0 ) % mod ) % mod;
			f[i + 1][j][k | 1][h ^ 1] = ( f[i + 1][j][k | 1][h ^ 1] + f[i][j][k][h] * ( j ? mi[i - 1] : mi[i] ) % mod ) % mod;
		}
	}
	int ans = 0;
	for( int j = 0;j <= 1;j ++ )
	for( int k = 0;k <= 1;k ++ )
		ans = ( ans + f[n][j][k][1] ) % mod;
	printf( "%lld\n", ans );
	return 0;
}

赢家

在这里插入图片描述 n ≤ 15 , m ≤ n × ( n + 1 ) 2 n\le 15,m\le \frac{n\times (n+1)}{2} n15,m2n×(n+1)


转化为用总数 2 m 2^m 2m减去不合法的方案数

不合法方案数即为, 1 1 1能到达的点集 S S S 2 2 2能到达的点集为 T T T S ∩ T = ∅ S∩T=\emptyset ST=

f [ S ] f[S] f[S]表示能使 1 1 1到达点集为 S S S内所有点的方案数, g [ T ] g[T] g[T]为能使 2 2 2到达点集为 T T T内所有点的方案数

枚举 S , T S,T S,T,两个集合内部的边的定向方案数即为 f [ S ] × g [ T ] f[S]\times g[T] f[S]×g[T](不能有边跨越 S , T S,T S,T

对于点集 S ∪ T S∪T ST的补集中的点,内部边可以随便定向 2 e d g e 2^{edge} 2edge,而对于一个顶点在集合外另一个顶点在 S , T S,T S,T集合内的边,一定是从集合外指向集合内

枚举的时间复杂度为 O ( 3 n ) O(3^n) O(3n)

接下来考虑怎么计算 f [ S ] f[S] f[S] g [ T ] g[T] g[T]与之一样

一样的思路,用总数减去不合法的数量

总数为 2 e d g e _ S 2^{edge\_S} 2edge_S

减去不合法的方案,枚举一个 S S S的真子集 s ′ s' s,计算只能到达子集 s ′ s' s内的点的方案数

点集 s ’ s’ s内的方案数为 f [ s ′ ] f[s'] f[s],点集外的方案数为 2 e d g e _ S − e d g e _ s ’ 2^{edge\_S-edge\_s’} 2edge_Sedge_s

对于横跨 s ’ , C S s ′ s’,C_{S}s' s,CSs的边,方向一定是从外面指向子集 s ′ s' s

所以此时减去的方案数为 f [ s ′ ] × 2 e d g e _ S − e d g e _ s ′ f[s']\times 2^{edge\_S-edge\_s'} f[s]×2edge_Sedge_s

枚举子集, D P DP DP时间复杂度为 O ( 3 n ) O(3^n) O(3n)

#include <cstdio>
#define mod 1000000007
#define int long long
#define maxn 20
#define maxm 1 << 15
int n, m, id;
bool edge[maxn][maxn];
int in[maxm], out[maxm], mi[maxn * maxn], f[maxm], g[maxm];

signed main() {
	scanf( "%lld %lld %lld", &n, &m, &id );
	mi[0] = 1;
	for( int i = 1, u, v;i <= m;i ++ ) {
		scanf( "%lld %lld", &u, &v );
		edge[u][v] = 1;
		mi[i] = ( mi[i - 1] << 1 ) % mod;
	}
	int cnt = 1 << n;
	for( int S = 0;S < cnt;S ++ )
		for( int i = 1;i <= n;i ++ )
			for( int j = 1;j <= n;j ++ )
				if( edge[i][j] ) {
					if( ( 1 << i - 1 & S ) && ( 1 << j - 1 & S ) ) in[S] ++;//完全包含在点集S里面的边
					if( ( 1 << i - 1 & S ) || ( 1 << j - 1 & S ) ) out[S] ++;//完全包含在点集S里面的边+一个顶点在点集里一个顶点在点集外
				}
	for( int S = 0;S < cnt;S ++ ) {
		if( ! ( S & 1 ) ) continue;//如果没有包含点1 跳过
		f[S] = mi[in[S]];
		for( int T = ( S - 1 ) & S;T;T = ( T - 1 ) & S ) {
			if( ! ( T & 1 ) ) continue;//子集也必须包含点1
			f[S] = ( f[S] - f[T] * mi[in[S ^ T]] % mod + mod ) % mod;
		}
	}
	for( int S = 0;S < cnt;S ++ ) {
		if( ! ( S >> 1 & 1 ) ) continue;
		g[S] = mi[in[S]];
		for( int T = ( S - 1 ) & S;T;T = ( T - 1 ) & S ) {
			if( ! ( T >> 1 & 1 ) ) continue;
			g[S] = ( g[S] - g[T] * mi[in[S ^ T]] % mod + mod ) % mod;
		}
	}
	int ans = mi[m];
	for( int S = 0;S < cnt;S ++ ) { 
		if( ! ( S & 1 ) || ( S >> 1 & 1 ) ) continue;
		for( int T = ( cnt - 1 ) ^ S;T;T = ( T - 1 ) & ( ( cnt - 1 ) ^ S ) ) {
			if( ! ( T >> 1 & 1 ) || in[S] + in[T] < in[S | T] ) continue;//如果没有包含点2 或 S,T点集有边横跨两个集合 为不合法划分 跳过
			ans = ( ans - f[S] * g[T] % mod * mi[m - out[S | T]] % mod + mod ) % mod;
		}
	}
	printf( "%lld\n", ans );
	return 0;
}

黑红兔

在这里插入图片描述 n ≤ 5 e 5 n\le 5e5 n5e5


性质1:存在一种方案,最后一段长度为 1 1 1,每选出的段的长度都比上一段小 1 1 1

很显然,如果某一段比下一段长 ≥ 2 \ge 2 2,可以在前面或者后面去掉若干字符,只需要保证下一段是严格子串即可

f [ i ] [ j ] f[i][j] f[i][j]表示以子串 [ i , j ] [i,j] [i,j]为首串,能否找出 j − i + 1 j-i+1 ji+1段符合要求

f f f y e s / n o yes/no yes/no b o o l bool bool数组

枚举下一段与 f [ i + 1 , j ] f[i+1,j] f[i+1,j]还是 f [ i ] [ j − 1 ] f[i][j-1] f[i][j1]进行转移

h a s h hash hash判断两个串是否相同

性质2:答案不超过 O ( n ) O(\sqrt{n}) O(n )

最好的情况为 1 + 2 + . . . + k 1+2+...+k 1+2+...+k,此时有 k ( k + 1 ) 2 ≤ n \frac{k(k+1)}{2}\le n 2k(k+1)n

性质3:假设以 i i i作为第一段开头,如果第一个串长 l e n len len时,可以选出 l e n len len段,那么串长为 l e n − 1 len-1 len1时,也能选出 l e n − 1 len-1 len1

非常显然,都删去一个首/尾跟下一段无关的字符,最后一段被删去,仍能保证严格子串性质

f [ i ] f[i] f[i]为以 i i i开始的首串,最长能选多少段

考虑二分答案,问题转化为找 [ i + m i d , n ] [i+mid,n] [i+mid,n]内是否存在一个 j j j,满足

f [ j ] ≥ m i d − 1 f[j]\ge mid-1 f[j]mid1

l c p ( i , j ) ≥ m i d − 1 lcp(i,j)\ge mid-1 lcp(i,j)mid1或者 l c p ( i + 1 , j ) ≥ m i d − 1 lcp(i+1,j)\ge mid-1 lcp(i+1,j)mid1(看是首/尾是新添的多余字符

如果求出原串的后缀数组,那么 l c p ( i , j ) ≥ x lcp(i,j)\ge x lcp(i,j)x相当于 r n k j rnk_j rnkj在某个区间内,可以二分求出这个区间

此套路做法,详情可见👉亲爱的佳媛姐姐正解做法——字符串LOJ2059

O ( n l o g 2 n ) O(nlog^2n) O(nlog2n)

性质4: f [ i ] ≤ f [ i + 1 ] + 1 f[i]\le f[i+1]+1 f[i]f[i+1]+1

如果 i i i开始能接大于 f [ i + 1 ] + 1 f[i+1]+1 f[i+1]+1段,那么 i + 1 i+1 i+1开始一定能接大于 f [ i + 1 ] + 1 − 1 = f [ i + 1 ] f[i+1]+1-1=f[i+1] f[i+1]+11=f[i+1]段,有性质3得出

所以就不用二分了,类似滑动窗口一样,先把 f [ i ] f[i] f[i]赋为 f [ i + 1 ] + 1 f[i+1]+1 f[i+1]+1,然后判断是否可行,不行就一直 − 1 -1 1直到可行为止

类似于 S A SA SA h e i g h t height height数组, O ( n l o g n ) O(nlogn) O(nlogn)

预处理 s t st st表里面的 l o g log log,快了整整三秒,卡(>ρ<")了

终于过了(^U^)ノ~YO

#include <cstdio>
#include <cstring>
#include <iostream>
using namespace std;
#define maxn 500005
#define INF 0x7f7f7f7f
int n, m = 255;
char s[maxn];
int tot[maxn], rnk[maxn << 1], sa[maxn], id[maxn], x[maxn], h[maxn], lg[maxn];
int st[maxn][20];

void init() {
	for( int i = 1;i <= n;i ++ ) tot[x[i] = s[i]] ++;
	for( int i = 1;i <= m;i ++ ) tot[i] += tot[i - 1];
	for( int i = n;i;i -- ) sa[tot[x[i]] --] = i;
	for( int k = 1;k <= n;k <<= 1 ) {
		int num = 0;
		for( int i = n - k + 1;i <= n;i ++ ) id[++ num] = i;
		for( int i = 1;i <= n;i ++ ) if( k < sa[i] ) id[++ num] = sa[i] - k;
		memset( tot, 0, sizeof( tot ) );
		for( int i = 1;i <= n;i ++ ) tot[x[i]] ++;
		for( int i = 1;i <= m;i ++ ) tot[i] += tot[i - 1];
		for( int i = n;i;i -- ) sa[tot[x[id[i]]] --] = id[i];
		for( int i = 1;i <= n;i ++ ) rnk[i] = x[i];
		x[sa[1]] = num = 1;
		for( int i = 2;i <= n;i ++ )
			x[sa[i]] = ( rnk[sa[i]] == rnk[sa[i - 1]] && rnk[sa[i] + k] == rnk[sa[i - 1] + k] ) ? num : ++ num;
		if( n == num ) break;
		m = num;
	}
	for( int i = 1;i <= n;i ++ ) rnk[sa[i]] = i;
	int k = 0;
	for( int i = 1;i <= n;i ++ ) {
		if( rnk[i] == 1 ) continue;
		if( k ) k --;
		int j = sa[rnk[i] - 1];
		while( i + k <= n && j + k <= n && s[i + k] == s[j + k] ) k ++;
		h[rnk[i]] = k;
	}
	lg[0] = -1;
	for( int i = 1;i <= n;i ++ ) lg[i] = lg[i >> 1] + 1;
	for( int i = 1;i <= n;i ++ ) st[i][0] = h[i];
	for( int j = 1;j <= 18;j ++ )
		for( int i = 1;i <= n;i ++ )
			if( i + ( 1 << j - 1 ) > n ) break;
			else st[i][j] = min( st[i][j - 1], st[i + ( 1 << j - 1 )][j - 1] );
}

int lcp( int l, int r ) {
	int i = lg[r - l + 1];
	return min( st[l][i], st[r - ( 1 << i ) + 1][i] );
}

int cnt;
int rt[maxn], t[maxn * 30], lson[maxn * 30], rson[maxn * 30];

void modify( int pre, int &now, int l, int r, int pos, int val ) {
	if( ! now ) now = ++ cnt;
	if( l == r ) { t[now] = max( t[now], val ); return; }
	int mid = ( l + r ) >> 1;
	if( pos <= mid ) rson[now] = rson[pre], modify( lson[pre], lson[now], l, mid, pos, val );
	else lson[now] = lson[pre], modify( rson[pre], rson[now], mid + 1, r, pos, val );
	t[now] = max( t[lson[now]], t[rson[now]] );
}

int query( int now, int l, int r, int L, int R ) {
	if( ! now || R < l || r < L ) return 0;
	if( L <= l && r <= R ) return t[now];
	int mid = ( l + r ) >> 1;
	return max( query( lson[now], l, mid, L, R ), query( rson[now], mid + 1, r, L, R ) );
}

int find_l( int pos, int len ) {
	int l = 1, r = pos - 1;
	while( l <= r ) {
		int mid = ( l + r ) >> 1;
		if( lcp( mid + 1, pos ) >= len ) r = mid - 1;
		else l = mid + 1;
	}
	return l;
}

int find_r( int pos, int len ) {
	int l = pos + 1, r = n;
	while( l <= r ) {
		int mid = ( l + r ) >> 1;
		if( lcp( pos + 1, mid ) >= len ) l = mid + 1;
		else r = mid - 1;
	}
	return r;
}

bool check( int pos, int len ) {
	if( query( rt[pos + len], 1, n, find_l( rnk[pos], len - 1 ), find_r( rnk[pos], len - 1 ) ) >= len - 1 )
		return 1;
	if( query( rt[pos + len], 1, n, find_l( rnk[pos + 1], len - 1 ), find_r( rnk[pos + 1], len - 1 ) ) >= len - 1 )
		return 1;
	return 0;
}

int ans;
int f[maxn];

int main() {
	scanf( "%s", s + 1 );
	n = strlen( s + 1 );	
	init();
	ans = f[n] = 1;
	modify( rt[n + 1], rt[n], 1, n, rnk[n], f[n] );
	for( int i = n - 1;i;i -- ) {
		f[i] = f[i + 1] + 1;
		while( ! check( i, f[i] ) ) f[i] --;
		ans = max( ans, f[i] );
		modify( rt[i + 1], rt[i], 1, n, rnk[i], f[i] );
	}
	printf( "%d\n", ans );
	return 0;
}
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值