zoukankan      html  css  js  c++  java
  • hdu2609 How many【最小表示法】【Hash】

    How many

    Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)
    Total Submission(s): 4210    Accepted Submission(s): 1936


    Problem Description
    Give you n ( n < 10000) necklaces ,the length of necklace will not large than 100,tell me
    How many kinds of necklaces total have.(if two necklaces can equal by rotating ,we say the two necklaces are some).
    For example 0110 express a necklace, you can rotate it. 0110 -> 1100 -> 1001 -> 0011->0110.
     
    Input
    The input contains multiple test cases.
    Each test case include: first one integers n. (2<=n<=10000)
    Next n lines follow. Each line has a equal length character string. (string only include '0','1').
     
    Output
    For each test case output a integer , how many different necklaces.
     
    Sample Input
    4 0110 1100 1001 0011 4 1010 0101 1000 0001
     
    Sample Output
    1 2
     
    Author
    yifenfei
     
    Source
     
    Recommend
    yifenfei
     

    题意:

    给定n个01串,统计一共有多少种不同的。如果他们的循环同构是相同的那他们就是相同的。

    思路:

    刚开始很暴力的把每个串的所有循环同构串都丢进set里,直接MLE了。太暴力了。

    应该要想到如果串相同的话,他们的最小表示法肯定是一样的。所以只需要存最小表示法就可以了。

    然后也不需要统计,直接print set的大小就可以了。

    每输入一个数,找到他的最小表示法。

    然后对这个最小表示法进行hash,结果丢进set

    处理完所有字符串,print set的大小。

     1 #include<iostream>
     2 #include<bits/stdc++.h>
     3 #include<cstdio>
     4 #include<cmath>
     5 //#include<cstdlib>
     6 #include<cstring>
     7 #include<algorithm>
     8 //#include<queue>
     9 #include<vector>
    10 //#include<set>
    11 //#include<climits>
    12 //#include<map>
    13 using namespace std;
    14 typedef long long LL;
    15 typedef unsigned long long ull;
    16 #define N 100010
    17 #define pi 3.1415926535
    18 #define inf 0x3f3f3f3f
    19 
    20 const int maxn = 1e4 + 4;
    21 int n;
    22 char str[105 * 2];
    23 ull h[105];
    24 set<ull>types;
    25 
    26 int main()
    27 {
    28     while(scanf("%d", &n) != EOF){
    29         types.clear();
    30         for(int i = 0; i < n; i++){
    31             scanf("%s", str + 1);
    32             int len = strlen(str + 1);
    33             for(int j = 1; j <= len; j++)str[len + j] = str[j];
    34             int j = 1, k = 2, p;
    35             while(j <= len && k <= len){
    36                 for(p = 0; p < n && str[j + p] == str[k + p];p++);
    37                 if(p == len)break;
    38                 if(str[j + p] > str[k + p]){
    39                     j = j + p + 1;
    40                     if(j == k)j++;
    41                 }
    42                 else{
    43                     k = k + p + 1;
    44                     if(j == k)k++;
    45                 }
    46             }
    47             int pos = min(j, k);
    48 
    49             for(j = 1; j <= len; j++){
    50                 h[j] = h[j - 1] * 131 + str[j + pos - 1] - '0';
    51             }
    52             types.insert(h[len]);
    53         }
    54         printf("%d
    ", types.size());
    55     }
    56     return 0;
    57 }
  • 相关阅读:
    了解jQuery
    了解JavaScript
    了解DOM
    了解CSS
    UICollectionViewCell点击高亮效果(附带效果GIF)
    产品迭代缓慢的原因
    了解Web的相关知识
    HTML常用标签
    HTML常用标签效果展示
    了解数据产品经理
  • 原文地址:https://www.cnblogs.com/wyboooo/p/9989622.html
Copyright © 2011-2022 走看看