现在的位置: 首页 > 综合 > 正文

POJ 2159 Ancient Cipher

2018年01月17日 ⁄ 综合 ⁄ 共 3232字 ⁄ 字号 评论关闭
Ancient Cipher
Time Limit: 1000MS   Memory Limit: 65536K
Total Submissions: 29060   Accepted: 9513

Description

Ancient Roman empire had a strong government system with various departments, including a secret service department. Important documents were sent between provinces and the capital in encrypted form to prevent eavesdropping. The most popular ciphers in those
times were so called substitution cipher and permutation cipher. 
Substitution cipher changes all occurrences of each letter to some other letter. Substitutes for all letters must be different. For some letters substitute letter may coincide with the original letter. For example, applying substitution cipher that changes
all letters from 'A' to 'Y' to the next ones in the alphabet, and changes 'Z' to 'A', to the message "VICTORIOUS" one gets the message "WJDUPSJPVT". 
Permutation cipher applies some permutation to the letters of the message. For example, applying the permutation <2, 1, 5, 4, 3, 7, 6, 10, 9, 8> to the message "VICTORIOUS" one gets the message "IVOTCIRSUO". 
It was quickly noticed that being applied separately, both substitution cipher and permutation cipher were rather weak. But when being combined, they were strong enough for those times. Thus, the most important messages were first encrypted using substitution
cipher, and then the result was encrypted using permutation cipher. Encrypting the message "VICTORIOUS" with the combination of the ciphers described above one gets the message "JWPUDJSTVP". 
Archeologists have recently found the message engraved on a stone plate. At the first glance it seemed completely meaningless, so it was suggested that the message was encrypted with some substitution and permutation ciphers. They have conjectured the possible
text of the original message that was encrypted, and now they want to check their conjecture. They need a computer program to do it, so you have to write one.

Input

Input contains two lines. The first line contains the message engraved on the plate. Before encrypting, all spaces and punctuation marks were removed, so the encrypted message contains only capital letters of the English alphabet. The second line contains the
original message that is conjectured to be encrypted in the message on the first line. It also contains only capital letters of the English alphabet. 
The lengths of both lines of the input are equal and do not exceed 100.

Output

Output "YES" if the message on the first line of the input file could be the result of encrypting the message on the second line, or "NO" in the other case.

Sample Input

JWPUDJSTVP
VICTORIOUS

Sample Output

YES

Source

题目大意:

就是说给你两个串A,B,问串A能不能通关某些变化得到串B,当然对串A的操作要对于其中的每一个字母有相同的操作(比如说,A-B,B->C,C->D....Y->Z,Z->A)

然后在通过将现在的A'串经过一个排列,也就是我们一般意义的排列算法,abbca ->aabbc这样做的.如果两个串A,B存在这种对应的关系,那么我们就输出 YES,否则输出NO...

解题思路:

这题读完后,感觉很难,因为A->A'的变化太多了,不知道改怎么把握,而A'->B的变化缺很简单,就是一个序列的不同排列而已,很容易判断,于是死坑不出来,就去搜题解了,看到了小U的blog,上面说,无论A->A',还是A'->B,我们只需要让一个串中字母的种类数保持不变就好.也就是说如果原来的A="ABCD"->变为了B.B="GHJK",每个字母都出现了一次,那么我们就有理由相信A->B的变化是存在的,如果A="ABCD",而B="UIO",那么这个串的字母种类却变少了,有原来的4个字母变为了现在的3个字母,那么我们就说这个由A->B的变化是不存在的,所以呢,,,接来来只需要枚举26个状态,然后对他们进行排序就OK了,如果排出来的序列相同(注意排列的是字母的种类数)那么我就输出YES!

代码:

# include<cstdio>
# include<iostream>
# include<algorithm>
# include<string>
# include<cstring>

using namespace std;

int num1[100];
int num2[100];

int main(void)
{
    string input;

    cin>>input;
    for ( int i = 0;i < input.length();i++ )
        {
            num1[input[i]-'A']++;
        }
    cin>>input;
    for ( int i = 0;i < input.length();i++ )
        {
            num2[input[i]-'A']++;
        }

    sort(num1,num1+26);
    sort(num2,num2+26);

    int flag = 0;
    for ( int i = 0;i < 26;i++ )
        {
            if ( num1[i]!=num2[i] )
                {
                    flag = 1;
                    break;
                }

        }
        if ( flag )
            cout<<"NO"<<endl;
            else
                cout<<"YES"<<endl;






    return 0;
}

抱歉!评论已关闭.