题意:给n个数组,任意两两拼接,总拼接数有n^2种,所以自身拼接一次,并且AB!=BA,求拼接后满足i<j,a[i]<a[j](称为‘上升’)至少一次的拼接数。
思路:情况1:自身存在上升,则该数组与任意拼接都存在上升,即2*n-1种都上升。
情况2:两两不存在上升,所以,只要存在前一个数组的最小值小于后一个数组的最大值即存在上升。
代码直接参考
————————————————
版权声明:本文为CSDN博主「骑猪大侠」的原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接及本声明。
代码链接:https://blog.csdn.net/m0_43449107/article/details/103840294
#include<bits/stdc++.h> typedef long long ll; const int N=1e6+1; using namespace std; int a[N], mx[N] ,pre[N]; int main() { int n, x, flag, mn, l; ll ans=0; scanf("%d", &n); for(int i=0; i<n; i++) { cin>>l; flag=0; mn=N; for(int j=0; j<l; j++) { scanf("%d", &x); if(mn<x) flag=1; //存在这么一对索引的序列标记一下 mx[i]=max(x, mx[i]), mn=min(x, mn); } if(flag) mn=-1, mx[i]=N-1; //所有的序列可以和它组合,他也可以和其他所有序列组合 pre[mn+1]++; } for(int i=1; i<N; i++) { pre[i]+=pre[i-1]; //最小值的前缀数组 } for(int i=0; i<n; i++) { ans+=pre[mx[i]]; //对于每个序列的最大值,看前面有多少个序列的最小值是小于这个序列的 } printf("%lld\n", ans); return 0; } ———————————————— 版权声明:本文为CSDN博主「骑猪大侠」的原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接及本声明。 原文链接:https://blog.csdn.net/m0_43449107/article/details/103840294