hdu5225 Tom and permutation(BestCoder Round #40)

Tom and permutation

Accepts: 120

Submissions: 422

Time Limit: 2000/1000 MS (Java/Others)

Memory Limit: 65536/65536 K (Java/Others)

问题描述

Tom学会了通过写程序求出一个1-n的排列的逆序对数,但他的老师给了他一个难题:
给出一个1-n的排列,求所有字典序比它小的1-n的排列的逆序对数之和。
Tom一时不知道该怎么做,所以他来找你帮他解决这个问题。
因为数可能很大,答案对109+7取模。

输入描述

输入包含多组数据(大约20组)。对于每一组数据,第一行一个正整数n,第二行n个数,是一个n的排列。
n≤100

输出描述

对于每组数据输出一行,答案模109+7。

输入样例

3
2 1 3
5
2 1 4 3 5

输出样例

1
75

Hint

由于输入文件可能较大,建议对读入进行优化
当时看不懂题意,后来问了问群里的朋友。
题意是:
 首先列举出所有比给定序列字典序小的序列, 然后对于每个列举出来的序列,求逆序数和, 然后对所有逆序数和再求和, 就是所求答案 
#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<cmath>
#include<algorithm>
#define maxn 110
#define mod 1000000007
using namespace std;
typedef long long LL;
typedef unsigned long long ULL;
int n,a[maxn],F[maxn],fact[maxn];
void Prepare(int n){
    fact[0]=1;
    for(int i=1;i<=n;i++)
        fact[i]=(LL)fact[i-1]*i%mod,F[i]=(LL)i*(i-1)/2*fact[i]%mod*(1+mod)/2%mod;
}
void read(){
    for(int i=1;i<=n;i++) scanf("%d",a+i);
}
int work(){
    static bool use[maxn];
    static int sum[maxn];
    int ans=0;
    memset(sum,0,sizeof(sum));
    memset(use,false,sizeof(use));
    int cnt=0;
    for(int i=1;i<=n;i++){
        for(int j=1;j<a[i];++j)
        if(!use[j]){
            LL val=0;
            for(int k=1;k<i;++k)
                val+=a[k]>j;
            val+=cnt;
            for(int k=1;k<=n;++k)
            if(k!=j&&!use[k]){
                val+=sum[k];
                val+=k<j;
            }
            val%=mod;
            ans=(ans+val*fact[n-i]+F[n-i])%mod;
        }
        for(int j=1;j<i;++j)
            cnt+=a[j]>a[i];
        for(int j=a[i];j>=1;--j)
            ++sum[j];
        use[a[i]]=true;
    }
    return ans;
}
int main()
{
    Prepare(100);
    while(cin>>n){
        read();
        cout<<work()<<endl;
    }
    return 0;
}

时间: 2024-11-05 22:48:50

hdu5225 Tom and permutation(BestCoder Round #40)的相关文章

HDU 5224 Tom and paper(BestCoder Round #40)

题目链接:Tom and paper 题面: Tom and paper Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others) Total Submission(s): 679    Accepted Submission(s): 432 Problem Description There is a piece of paper in front of Tom, its length

HDU5226 Tom and matrix(BestCoder Round #40)

Tom and matrix Accepts: 29 Submissions: 225 Time Limit: 3000/1500 MS (Java/Others) Memory Limit: 65536/65536 K (Java/Others) 问题描述 Tom放学回家的路上,看到天空中出现一个矩阵.Tom发现,如果矩阵的行.列从0开始标号,第i行第j列的数记为ai,j,那么ai,j=Cji 如果i < j,那么ai,j=0 Tom突发奇想,想求一个矩形范围内所有数的和.Tom急着回家,当然

HDU5224 Tom and paper(BestCoder Round #40)

Tom and paper Accepts: 464 Submissions: 955 Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/65536 K (Java/Others) 问题描述 Tom面前有一张纸,它的长和宽都是整数.Tom知道这张纸的面积n,他想知道这张纸的周长最小是多少. 输入描述 有多组数据.第一行一个正整数T,表示数据组数.接下来T行,每行一个正整数n,表示纸的面积. T≤10,n≤109 输出描述 对于每

BestCoder Round #40 1001——精度——Tom and paper

Problem Description There is a piece of paper in front of Tom, its length and width are integer. Tom knows the area of this paper, he wants to know the minimum perimeter of this paper. Input In the first line, there is an integer T indicates the numb

BestCoder Round #40

弱渣做不动CF了,弱渣只能水水BC了,于是就开始每周开心地BC了,顺便写个水水的题解~~ 题A hdu 5224 题意:略 题解:枚举边长即可. 1 /*zhen hao*/ 2 #include <bits/stdc++.h> 3 using namespace std; 4 5 #define lson l, m, rt*2 6 #define rson m + 1, r, rt*2+1 7 #define xx first 8 #define yy second 9 10 typedef

BestCoder Round #40 解题报告

这场是第一场没有米的BC... 大概也是想震一震那些一听说没米了就不打BC的人吧 这次的题目质量比以往高了许多 (然而我并没有打这一场BC 但是今天下午到现在做的过程中真的学到了不少知识呢 A题略水... 1 #include<cstdio> 2 #include<cstdlib> 3 #include<cstring> 4 #include<cmath> 5 int T,n; 6 int main(){ 7 scanf("%d",&am

HDU5225 Tom and permutation(排列组合)

题意: Tom学会了通过写程序求出一个1-n的排列的逆序对数,但他的老师给了他一个难题: 给出一个1-n的排列,求所有字典序比它小的1-n的排列的逆序对数之和. Tom一时不知道该怎么做,所以他来找你帮他解决这个问题. 因为数可能很大,答案对109+7取模. 从前往后推,先计算1-k的所有排列可以产生逆序总数, 先假设db[2]为1-2的结果,那么我们来看3的排列,他是由1[2,3],2[1,3],3[1,2]三项组成,[]为所有排列的意思,第一项中[2,3]组合对结果贡献db[2],前面的1小

BestCoder Round #40 A B C

A,水题,直接枚举到sqrt B,每次对于每一位枚举,如果小于当前位,那么答案可以计算出来,增加得答案为:设3个部分,前完全一样的部分a,中间新选的一个b,后面的全排列c,这样就把每部分和每两部分能够组成的逆序对个数计算出来,由于n只有100,里面在去枚举也是没问题的,主要是后面全排列c的逆序对数,这个可以利用dp处理出来,dp[i] = dp[i - 1] * i + i! * sum(i - 1),sum(i)表示1到i的和. C:推公式,C(n, m) = C(n - 1, m - 1)

[BestCoder Round #7] hdu 4985 Little Pony and Permutation (找循环节)

Little Pony and Permutation Problem Description As a unicorn, the ability of using magic is the distinguishing feature among other kind of pony. Being familiar with composition and decomposition is the fundamental course for a young unicorn. Twilight