BZOJ 3555: [Ctsc2014]企鹅QQ

本文介绍了解决BZOJ3555题目[Ctsc2014]企鹅QQ的方法,通过计算字符串的哈希值,删除每个位置的字符并进行排序,最后统计相同字符串的数量。

二次联通门 : BZOJ 3555: [Ctsc2014]企鹅QQ

 

 

 

 

 

/*
    BZOJ 3555: [Ctsc2014]企鹅QQ

    哈希
    
    先处理出所有串的哈希值
    后枚举每一位, 删去该位 

    排序
    统计相同的个数即可 
*/
#include <algorithm>
#include <cstring>
#include <cstdio>

void read (int &now)
{
    register char word = getchar ();
    bool temp = false;
    for (now = 0; word < '0' || word > '9'; word = getchar ())
        if (word == '-')
            temp = true;
    for (; word >= '0' && word <= '9'; now = now * 10 + word - '0', word = getchar ());
    if (temp)
        now = -now;
}

#define Max 30006
char line[Max / 150];

unsigned long long Hash;
#define L 233

int Len;
unsigned long long mi[L];

unsigned long long Get_Hash (char *key)
{
    Hash = 0;
    for (int i = 0; i < Len; i ++)
        Hash = Hash * L + key[i];
    
    return Hash;
}

unsigned long long hash[Max * 210];

int main (int argc, char *argv[])
{
    int N, M, K;
    read (N);
    read (M);
    read (K);
    Len = M;
    register int i, j;
    mi[0] = 1;
    for (int i = 1; i <= L; i ++)
        mi[i] = mi[i - 1] * L;
        
    int cur = 0;
    unsigned long long res;
    for (i = 1; i <= N; i ++)
    {
        scanf ("%s", line);
        res = Get_Hash (line);
        
        for (j = 0; j < Len; j ++)
            hash[++ cur] = res - mi[Len - j - 1] * line[j];
    }

    std :: sort (hash + 1, hash + 1 + cur);
    long long Answer = 0;
    K = 1;
    for (i = 2; i <= cur; i ++)
        if (hash[i] == hash[i - 1])
            K ++;
        else
        {
            Answer += K * (K - 1) / 2;
            K = 1;
        }
    Answer += K * (K - 1) / 2;
    
    printf ("%lld", Answer);
    return 0;
}

 

转载于:https://www.cnblogs.com/ZlycerQan/p/7299630.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值