在 Java 中将字符串转换为小型大写伪字母

Converting a String to small caps pseudoalphabet in Java

我找到了一个网站 which can convert any text to different obscure unicode font styles,例如Small Caps pseudoalphabet.

我有兴趣在 Java 代码中做同样的事情。以下 HxD 屏幕截图显示了两个文本版本的字节数:

有什么方法可以使用内置方法或库在 Java 中进行转换吗?结果最好是另一个 String 对象。

引用您链接的网站:

What makes an alphabet "psuedo"?

One or more of the letters transliterated has a different meaning or source than intended. In the non-bold version of Fraktur, for example, several letters are "black letter" but most are "mathematical fraktur". In the Faux Cyrillic and Faux Ethiopic, letters are selected merely based on superficial similarities, rather than phonetic or semantic similarities.

所以没有明确定义的小型大写转换;相反,转换器的作者精心挑选了代码点映射以提供所需的效果。

对于小型大写字母,这可能是因为 unicode 中没有 x 的小型大写字母版本。

为了重新创建相同的效果,您必须实施代码点转换查找 table(您可以通过例如将整个字母表传递给转换器来生成)

Unicode 规范对每个代码点都有一个正式的 stable 名称。您可以通过使用方法 Character.codePointOf(String).

查找“拉丁字母小写字母 c”来利用这一点
public static String translate(String s) {
    int len = s.length();
    Formatter smallCaps = new Formatter(new StringBuilder(len));
    for (int i = 0; i < len; i++) {
        char c = s.charAt(i);
        if (c >= 'A' && c <= 'Z' && c != 'X') {
            smallCaps.format("%c",
                Character.codePointOf("LATIN LETTER SMALL CAPITAL " + c));
        } else {
            smallCaps.format("%c", c);
        }
    }
    return smallCaps.toString();
}

我把 && c != 'X' 放在测试中是因为目前没有拉丁字母小写字母 X 字符,尽管 it has been proposed.

请注意,一些小写字母代码点可能不在 Java 的 Unicode 字符数据 table 的内部副本中。我发现我需要使用 Java 12 或更高版本才能识别它们。

我刚刚通过将纯文本字母表转换为 Unicode "small caps" 字母表找到了一个简单的解决方案,如下所示:

private static final String[] ALPHABET = "abcdefghijklmnopqrstuvwxyz".split("");
private static final String[] SMALL_CAPS_ALPHABET = "ᴀʙᴄᴅᴇꜰɢʜɪᴊᴋʟᴍɴᴏᴩqʀꜱᴛᴜᴠᴡxyᴢ".split("");

private static String toSmallCaps(String text)
{
    text = text.toLowerCase();
    StringBuilder convertedBuilder = new StringBuilder();
    for (char textCharacter : text.toCharArray())
    {
        int index = 0;
        boolean successfullyTranslated = false;
        for (String alphabetLetter : ALPHABET)
        {
            if ((textCharacter + "").equals(alphabetLetter))
            {
                convertedBuilder.append(SMALL_CAPS_ALPHABET[index]);
                successfullyTranslated = true;
                break;
            }

            index++;
        }

        if (!successfullyTranslated)
        {
            convertedBuilder.append(textCharacter);
        }
    }

    return convertedBuilder.toString();
}

用法:

String smallCaps = toSmallCaps("Hello Whosebug!");
System.out.println(smallCaps);

输出:

ʜᴇʟʟᴏ ꜱᴛᴀᴄᴋᴏᴠᴇʀꜰʟᴏᴡ!

这不是最优雅或可扩展的解决方案,但也许有人可以提出改进建议。

@BullyWiiPlaza 发布的 很好,但是代码效率很低。

这是一个替代实现,它会更快并且使用更少的内存:

private static final char[] SMALL_CAPS_ALPHABET = "ᴀʙᴄᴅᴇꜰɢʜɪᴊᴋʟᴍɴᴏᴩqʀꜱᴛᴜᴠᴡxyᴢ".toCharArray();

private static String toSmallCaps(String text)
{
    if(null == text) {
        return null;
    }
    int length = text.length();
    StringBuilder smallCaps = new StringBuilder(length);
    for(int i=0; i<length; ++i) {
        char c = text.charAt(i);
        if(c >= 'a' && c <= 'z') {
            smallCaps.append(SMALL_CAPS_ALPHABET[c - 'a']);
        } else {
            smallCaps.append(c);
        }
    }
    return smallCaps.toString();
}