首页 > 代码库 > hdu 2609 How many(最小表示法)

hdu 2609 How many(最小表示法)

题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=2609

题意:给你n个字符串每个字符串可以左右移动但还是同一串比如 0110 可以表示为 0110 -> 1100 -> 1001 -> 0011->0110

这些都属于同一个字符串,最后问这n个字符串里一共有多少不同的字符串

 

可以将这些字符串都以其最小表示方法存下来复杂度为O(n)然后在sort一遍找一下有几个不同的就行了。

 

#include <iostream>#include <cstring>#include <algorithm>using namespace std;const int M = 1e4 + 10;char sl[1000];struct TnT {    char sm[1000];}T[M];int Minnum(char s[] , int l){    int i = 0 , j = 1 , k = 0 , t;    while(i < l && j < l && k < l){        t = s[(i + k) >= l ? i + k - l : i + k] - s[(j + k) >= l ? j + k - l : j + k];        if(!t) k++;        else {            if(t > 0) i = i + k + 1;            else j = j + k + 1;            if(i == j) j++;            k = 0;        }    }    return i;}bool cmp(TnT a , TnT b) {    return strcmp(a.sm , b.sm) <= 0;}int main() {    int n;    while(scanf("%d" , &n) != -1) {        for(int i = 0 ; i < n ; i++) {            scanf("%s" , sl);            int len = strlen(sl);            int pos = Minnum(sl , len);            int num = 0;            for(int j = pos ; j < len ; j++) {                T[i].sm[num++] = sl[j];            }            for(int j = 0 ; j < pos ; j++) {                T[i].sm[num++] = sl[j];            }            T[i].sm[num] = ‘\0‘;        }        sort(T , T + n , cmp);        int ans = 1;        for(int i = 1 ; i < n ; i++) {            if(strcmp(T[i].sm , T[i - 1].sm) != 0) {                ans++;            }        }        printf("%d\n" , ans);    }    return 0;}

hdu 2609 How many(最小表示法)