首页 > 试题广场 >

小红的回文串

[编程题]小红的回文串
  • 热度指数:2141 时间限制:C/C++ 1秒,其他语言2秒 空间限制:C/C++ 256M,其他语言512M
  • 算法知识视频讲解
小红有一个字符串,她可以进行以下操作:
  • 拆分。把 'w' 拆成2个 'v',’m‘ 拆成 2个 'n'。
  • 轴对称。把 'b' 轴对称成 'd' ,'p' 轴对称成 'q',反之亦然。
  • 翻转。把 'b' 翻转成'q',把 'd' 翻转成 'p',把' n' 翻转成 'u',反之亦然。
经过若干次操作后,小红想知道这个字符串能不能变成回文串。

输入描述:
第一行输入一个整数 T(1 \leq T \leq 10^4) 表示询问次数。

接下来 T 行,每行输入一个字符串表示询问。

所有字符串长度之和不超过 10^5


输出描述:
输出 T 行,每行输出 "YES" 或 "NO" 表示是否可以变成回文串。
示例1

输入

5
wovv
bod
pdd
moom
lalalai

输出

YES
YES
YES
YES
NO

说明

第一个字符串可以变成:vvovv(将第一个w拆成两个v)
第二个字符串可以变成:bob、dod、pop或qoq
第三个字符串可以变成:bdb
第四个字符串本来就是回文的,不用进行操作
第五个字符串不可以变成回文串
def is_same(a:str,b:str)->bool:
    if a == b:
        return True
    else:
        if a in ['b','d','q','p'] and b in ['b','d','q','p']:
            return True
        elif a in ['n','u'] and b in ['n','u']:
            return True
        else:
            return False

def main():
    t = int(input())
    for _ in range(t):
        dest_s = ''
        s = input()
        for c in s:
            if 'w' == c :
                dest_s += 'vv'
            elif 'm' == c:
                dest_s += 'nn'
            else:
                dest_s += (c)
        l,r = 0,len(dest_s)-1
        flag = True
        while l < r:
            if not is_same(dest_s[l],dest_s[r]):
                flag = False
                break
            l+=1
            r-=1
        if flag:
            print('YES')
        else:
            print('NO')
        

if __name__ == '__main__':
    main()

发表于 2025-11-21 09:01:55 回复(0)
import java.util.Scanner;

// 注意类名必须为 Main, 不要有任何 package xxx 信息
public class Main {
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        int T = in.nextInt();
        while (T-- > 0) {
            String str = in.next();
            String str1 = str.replace("m", "nn");
            String str2 = str1.replace("w", "vv");
            int len = str2.length();
            boolean flag = true;
            for (int i = 0; i < len / 2; i++) {
                char c1 = str2.charAt(i);
                char c2 = str2.charAt(str2.length() - i - 1);
                if ((c1 == 'b' || c1 == 'd' || c1 == 'p' || c1 == 'q') && (c2 ==    'b' || c2 == 'd' || c2 == 'p' || c2 == 'q')) continue;
                if ((c1 == 'n' || c1 == 'u') && (c2 == 'n' || c2 == 'u')) continue;
                if (c1 != c2) {
                    flag = false;
                    break;
                }
            }
            if (flag) System.out.println("YES");
            else System.out.println("NO");
        }
    }
}

发表于 2025-08-29 12:23:18 回复(0)

注意一个字母可以多次变化

#include <algorithm>
#include <iostream>
#include <cmath>
#include <string>
using namespace std;

bool iss(string s) {

    int i = 0, j = s.size() - 1;

    while (i < j) {
        if ((s[i] == s[j]) || 
            (s[i] == 'q' && (s[j]==  'p' || s[j] == 'b' ||s[j]== 'd' )) ||
            (s[i] == 'p' && (s[j]==  'q' || s[j] == 'b' ||s[j]== 'd' )) ||
            (s[i] == 'd' && (s[j]==  'p' || s[j] == 'b' ||s[j]== 'q' )) ||
            (s[i] == 'b' && (s[j]==  'p' || s[j] == 'q' ||s[j]== 'd' )) ||

            (s[i] == 'n' && s[j] == 'u') || 
            (s[i] == 'u' && s[j] == 'n')) {
            i++;
            j--;
        } else if (((s[i] == 'n'||s[i]=='u') && i + 1 < j && 
                   (s[i + 1] == 'n'||s[i + 1] == 'u') && s[j] == 'm') ||
                   (s[i] == 'v' && i + 1 < j && s[i + 1] == 'v' && s[j] == 'w')) {

            i += 2;
            j--;
        }

        else if (((s[j] == 'n'||s[j]=='u') && j - 1 > i &&
                 (s[j - 1] == 'n'||s[j-1]=='u') && s[i] == 'm') ||
                 (s[j] == 'v' && j - 1 > i && s[j - 1] == 'v' && s[i] == 'w') ) {
            i ++;
            j -= 2;
        }
        else {
            return false;
        }
    }

    return true;

}


int main() {
    int n;
    cin >> n;
    while (n--) {
        string s;
        cin >> s;
        if (iss(s)) {
            cout << "YES" << endl;
        } else {
            cout << "NO" << endl;
        }


    }
}
// 64 位输出请用 printf("%lld")
发表于 2025-08-05 21:26:46 回复(0)
import java.util.*;

// 注意类名必须为 Main, 不要有任何 package xxx 信息
public class Main {
    private static final Set<Character> set1 = new HashSet<>();
    private static final Set<Character> set2 = new HashSet<>();
    static {
        set1.add('d');
        set1.add('p');
        set1.add('q');
        set1.add('b');
        set2.add('u');
        set2.add('n');
    }
    private static String s;
    private static int i ,j;
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        int t = in.nextInt();
        while (t-- > 0) {
            s = in.next();
            i = 0;
            j = s.length() - 1;
            System.out.println(f() ? "YES" : "NO");
        }
    }
    private static boolean f() {
        while (i <= j && ((s.charAt(i) == s.charAt(j)) || judge())) {
            i++;
            j--;
        }
        return i >= j;
    }
    private static boolean judge() {
        if (set1.contains(s.charAt(i)) && set1.contains(s.charAt(j))) return true;
        else if (set2.contains(s.charAt(i)) && set2.contains(s.charAt(j))) return true;
        else if (set1.contains(s.charAt(i)) || set1.contains(s.charAt(j))) return false;
        else {
            StringBuffer sb = new StringBuffer();
            if (s.charAt(i) == 'w' && s.charAt(j) == 'v') {

                sb.append(s, 0, i);
                sb.append("vv");
                ++j;
                s = sb.toString() + s.substring(i + 1);
                return true;
            } else if (s.charAt(i) == 'v' && s.charAt(j) == 'w') {

                sb.append(s.substring(0, j));
                sb.append("vv");
                s = sb.toString() + s.substring(j + 1);
                ++j;

                return true;
            } else if (s.charAt(i) == 'm' && (s.charAt(j) == 'n' || s.charAt(j) == 'u')) {

                sb.append(s.substring(0, i));
                sb.append("nn");

                ++j;
                s = sb.toString() + s.substring(i + 1);
                return true;
            } else if (s.charAt(j) == 'm' && (s.charAt(i) == 'n' || s.charAt(i) == 'u')) {
                sb.append(s.substring(0, j));
                sb.append("nn");
                s = sb.toString() + s.substring(j + 1);
                ++j;

                return true;
            } else return false;
        }


    }
}
//b d q p
//w -> v v
//m -> u u n n u n


发表于 2025-06-26 17:08:49 回复(0)
const rl = require("readline").createInterface({ input: process.stdin });
var iter = rl[Symbol.asyncIterator]();
const readline = async () => (await iter.next()).value;

void (async function () {
    // Write your code here
    const n = await readline();
    while ((line = await readline())) {
        let tokens = line.split(" ");
        // console.log(tokens);
        let splitStr = line.replace(/w/g, 'vv').replace(/m/g, 'nn');
        const getEquivalent = (c) => {
            if (c === "v") return "V";
            if (c === "n" || c === "u") return "N";
            if (["b", "d", "p", "q"].includes(c)) return "B";
            return c; // 其他字符等价类为自身
        };

        // 生成等价类数组
        const eqArr = splitStr.split("").map(getEquivalent);

        // 步骤3:检查等价类数组是否为回文
        const isPalindrome = eqArr.join("") === eqArr.reverse().join("");

        console.log(isPalindrome ? "YES" : "NO");
    }
})();

发表于 2025-10-24 10:49:03 回复(0)
我管你这那的
#include <algorithm>
#include <iostream>
using namespace std;

int main() {
    string s;
    int t;
    cin >> t;
    while(t--){
        cin >> s;
        int l = s.length();
        string res = "";
        for(char c : s){
            if(c == 'm') 
                res += "##";
            else if(c == 'w') 
                res += "vv";
            else if(c == 'b' || c == 'p' || c == 'd' || c == 'q')
                res += '*';
            else if(c == 'n' || c == 'u') 
                res += '#';
            else
                res += c;
        }  
        string ser = res;
        reverse(res.begin(), res.end());
                        //cout << res << "  " << ser;
        if(ser == res) cout << "YES";
        else cout << "NO";
        cout << endl;
    }
    return 0;
}
// 64 位输出请用 printf("%lld")


发表于 2025-10-21 20:46:06 回复(0)
直接全部替换,b=d=p=q,w=vv,n=u,m=nn=uu,遍历原字符串得到新串判断即可
#include <iostream>
#include<string>
using namespace std;

int main() {
    ios_base::sync_with_stdio(false);
    cin.tie(nullptr);
    int t;
    cin>>t;
    string s,_s;
    while(t--){
        cin>>s;
        _s="";
        int k=1;
        for(char ch:s){
            if(ch=='d'||ch=='p'||ch=='q')
            _s+='b';
            else if(ch=='w')
            _s+="vv";
            else if(ch=='m')
            _s+="uu";
            else if(ch=='n')
            _s+='u';
            else
            _s+=ch;
        }
        int left=0,right=_s.size()-1;
        while(left<right){
            if(_s[left]!=_s[right]){
            k=0;
            break;
            }
            left++;
            right--;
        }
        if(k==0)
        cout<<"NO\n";
        else
        cout<<"YES\n";
    }
}

发表于 2025-09-16 21:10:47 回复(0)
def is_huiwen(s):
    if s==s[::-1]:
        return True
    else:
        return False

def judge(s):
    s_cz = ''
    for j in s:
        if j in 'bdqp':
            s_cz += 'b'
        elif j=='w':
            s_cz += 'vv'
        elif j=='m':
            s_cz += 'nn'
        elif j=='u':
            s_cz += 'n'
        else:
            s_cz += j
    if is_huiwen(s_cz):
        print('YES')
    else:
        print('NO')

T = int(input())
for i in range(T):
    judge(input())
发表于 2025-08-25 19:20:33 回复(0)
自定义一个判断两字母的方法.将字符串中w,m拆分.
import java.util.*;

public class Main {
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        int n=in.nextInt();
        for(int i=0;i<n;i++){
            String s=in.next().trim();
            StringBuilder sb=new StringBuilder();
            for(int j=0;j<s.length();j++){
                char c=s.charAt(j);
                if(c=='w')
                    sb.append("vv");
                else if(c=='m')
                    sb.append("nn");
                else    
                    sb.append(c);
            }
            int l=0,r=sb.length()-1;
            boolean res=true;
            while(r>l){
                char a=sb.charAt(l);
                char b=sb.charAt(r);
                if(!equal(a,b)){
                    res=false;
                    break;
                }
                l++;
                r--;
            }
            System.out.println(res==true?"YES":"NO");
        }
               
       
    }

    public static boolean equal(char a,char b){
        List<Character> set=Arrays.asList('b','d','p','q');
        if(a=='n'&&b=='u'||a=='u'&&b=='n')
            return true;
        if(set.contains(a)&&set.contains(b))
            return true;
        return a==b;
    }
}

发表于 2025-08-05 09:01:08 回复(0)
有没有人救救孩子,在用例9的第97行出错了,这也调试不了啊

#include
<iostream>
using namespace std;

// b=d=p=q, n=u
// w->2v, m->2n
bool isMyPalindrome(const string& str) {
    int left = 0, right = str.size() - 1;

    while (right > left) {
        char a = str[left];
        char b = str[right];

        //==
        if (a == b) {
            ++left;
            --right;
        }

        //b,d,p,q
        else if ((a == 'b' || a == 'd' || a == 'p' ||
                  a == 'q')
                 && (b == 'b' || b == 'd' || b == 'p' ||
                     b == 'q')) {
            ++left;
            --right;
        }

        //n,u
        else if ((a == 'n' || a == 'u')
                 && (b == 'n' || b == 'u')) {
            ++left;
            --right;
        }

        //w
        else if (a == 'w' && b == 'v' && right - 1 > left && str[right - 1] == 'v') {
            ++left;
            right -= 2;
        }

        else if (b == 'w' && a == 'v' && left + 1 < right && str[left + 1] == 'v') {
            left += 2;
            --right;
        }

        //m
        else if (a == 'm' && b == 'n' && right - 1 > left && str[right - 1] == 'n') {
            ++left;
            right -= 2;
        }

        else if (b == 'm' && a == 'n' && left + 1 < right && str[left + 1] == 'n') {
            left += 2;
            --right;
        }

        else {
            return false;
        }
    }

    return true;
}

int main() {
    ios::sync_with_stdio(false);
    cin.tie(nullptr);

    int T;
    cin >> T;

    string str;
    while (T--) {
        cin >> str;
        if (isMyPalindrome(str)) {
            cout << "YES\n";
        } else {
            cout << "NO\n";
        }
    }
    return 0;
}
发表于 2025-07-18 15:02:15 回复(2)
def can_be_palindrome(s):

    if s == s[::-1]:
        return True
    
    # 替换拆分字符
    s = s.replace('w', 'vv').replace('m', 'nn')
    n = len(s)

    # 等价字符对(包括对称 & 翻转) 需要扩展等价关系
    equiv = {
        ('b', 'd'), ('b', 'p'), ('b', 'q'),
        ('d', 'b'), ('d', 'p'), ('d', 'q'),
        ('p', 'b'), ('p', 'd'), ('p', 'q'),
        ('q', 'b'), ('q', 'd'), ('q', 'p'),
        ('n', 'u'), ('u', 'n')
    }

    for i in range(n // 2):
        a = s[i]
        b = s[n - 1 - i]
        if a == b:
            continue
        elif (a, b) in equiv:
            continue
        else:
            return False
    return True

n = int(input().strip())

for i in range(n):
    s = input().strip()
    if can_be_palindrome(s):
        print('YES')
    else:
        print('NO')


发表于 2025-07-08 14:29:15 回复(0)
1
发表于 2025-03-28 16:28:48 回复(1)