1. 程式人生 > 其它 >Typecho 反序列化漏洞 分析及復現

Typecho 反序列化漏洞 分析及復現

luogu傳送門

題意簡述:

\(t\) 組資料。

每組資料給定一個數 \(x\) 以及一個長度為 \(n\) 的數列 \(a_1,a_2,…,a_n\)

\(|j-i|>=x(1\le i,j\le n)\) 時,你可以交換 \(a_i,a_j\)

問你能否將這個序列變為從小到大的。

\(\texttt{SOLUTION}\)

\(2\times x\le n\) 時,答案一定是 YES

因為我們可以通過 \(a_1,a_n\) 當中轉或直接交換排列中的任意兩個數字。

我來舉個例子:

如果 \(n=6,x=3\)

\(a={1\ 6\ 3\ 5\ 2\ 4}\)

  • 目標:交換 \(3\ 2\)
  • 操作:
    • 交換 \(3\ 4\)
    • 交換 \(2\ 1\)
    • 交換 \(2\ 3\)
    • 交換 \(2\ 4\)
    • 交換 \(3\ 1\)
  • 目標:交換 \(6\ 4\)
  • 操作:
    • 交換 \(6\ 4\)

\(2\times x\geq n\) 時,我們只能通過上述相同方法任意交換 \(a_1,a_2,…,a_{n-x}\)\(a_{x+1},a_{n-x+2},…,a_n\)

\(a_{n-x+1},a_{n-x+1},…,a_{x}\) 無法移動。

設將 \(a\) 從小到大排序後為 \(s\)

所以如果答案為 YES\(a_{n-x+1},a_{n-x+1},…,a_{x}\)

一定與 \(s_{n-x+1},s_{n-x+1},…,s_{x}\)相同。

否則答案就為 NO

\(\texttt{AC CODE}\)

#include<bits/stdc++.h>
using namespace std;
const int MAX=100010;
int read()
{
	int x=0; char ch=getchar();
	while(ch<'0'||ch>'9') ch=getchar();
	while(ch>='0'&&ch<='9') x=(x<<1)+(x<<3)+(ch^48),ch=getchar();
	return x;
}
int n,x,a[MAX],s[MAX];
bool check(int l,int r)
{
	for(int i=1;i<=n;i++) s[i]=a[i];
	sort(s+1,s+n+1);
	for(int i=l;i<=r;i++) if(a[i]!=s[i]) return 0;
	return 1;
}
int main()
{
	int t=read();
	while(t--)
	{
		n=read(),x=read();
		for(int i=1;i<=n;i++) a[i]=read();
		if(2*x<=n) puts("YES");
		else puts(check(n-x+1,x)?"YES":"NO");
	}
	return 0;
}