AtCoder 2316 思维题

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了AtCoder 2316 思维题相关的知识,希望对你有一定的参考价值。

题目链接:https://vjudge.net/problem/AtCoder-2316

 

题意:给你n个人的位置,每个人能往左跳一格或两格到无人的位置,跳到0位置,这个人消失。n个人消失组成一个排列,问有多少种排列。

 

感觉自己题目做得少也不是很聪明,这种手推规律或者说考验思维的题目还是很头疼啊。

最后看了zzh大佬非常简短的AC代码,又问了队友之后才终于懂了一丢丢,但是以后遇到怕是还是不会。

如果人是一个隔一个站的,也就是站在1 3 5 7 9...的位子上,那n个人就有 n! 种排列。

如果不是这种情况,那我们就要让其中一些人先出去来维持这样的情况。那么如何维持呢?

比如现在情况是1 3 4 5,那我们要让前面三个人中出去一个,有三种情况,然后其他三个人就有 3! 种情况。

所以总结一下就是,先定义ans = 1, k = 0表示现在队列里的人数。

依次读入人的位置,k++,直到有人不符合1 3 5 7...的情况,就ans *= k,然后k--。

这样就一直维持了1 3 5 7...这个状态,最后ans再乘k的阶乘就行啦。

最后要注意ans要用long long, 每步都要MOD。

 1 #include<cstdio>
 2 #include<cstring>
 3 #include<iostream>
 4 #include<algorithm>
 5 #include<cmath>
 6 #include<vector>
 7 #include<set>
 8 #include<string>
 9 #include<sstream>
10 #include<cctype>
11 #include<map>
12 #include<stack>
13 #include<queue>
14 #include<cstdlib>
15 #include<ctime>
16 using namespace std;
17 #define INF 0x3f3f3f3f
18 typedef long long ll;
19 int gcd(int a, int b){return b==0?a:gcd(b,a%b);}
20 
21 const int MOD = 1e9 + 7;
22 
23 int main()
24 {
25 //    freopen("input1.txt", "r", stdin);
26 //    freopen("output.txt", "w", stdout);
27     int n, x, k = 0;
28     ll ans = 1;
29     scanf("%d", &n);
30     while(n--)
31     {
32         scanf("%d", &x);
33         k++;
34         if(x < 2 * k - 1)
35         {
36             ans = ans * k % MOD;
37             k--;
38         }
39     }
40     for(int i = 2; i <= k; i++)
41         ans = ans * i % MOD;
42     printf("%d\n", (int)ans);
43     return 0;
44 }

 

以上是关于AtCoder 2316 思维题的主要内容,如果未能解决你的问题,请参考以下文章

AtCoder刷题记录

AtCoder Beginner Contest 100 C(思维)

Atcoder Grand Contest 054 题解

CODE FESTIVAL 2017 qual A C Palindromic Matrix(思维题)

AtCoder Beginner Contest 173 E - Multiplication 4 (思维)

AtCoder 杂题集