Java 代码中的表情符号 - 字符文字中的字符过多
Emoji symbol in Java code - Too many characters in character literal
我必须计算给定字符串中的字符数。我将计数保存到地图 Map<Character, Long>
。该代码不适用于某些特殊符号,例如“两颗心”。当我将这样的特殊符号转换为字符时,会出现编译器错误“字符文字中的字符过多”或类似错误。为什么会发生这种情况以及如何解决?
这里有一些粗略的代码来演示这个问题。这不是完整代码。
import java.util.HashMap;
import java.util.Map;
public class Demo {
public static void main(String[]args){
String twoHeartsStr = "";
Map<Character, Long> output = new HashMap<>();
output.put(twoHeartsStr.charAt(0), 1L);
//Compiler error:
//intellij IDE compiler : Too many characters in character literal.
//java: unclosed character literal.
Map<Character, Long> expectedOutput = Map.of('', 1L);
System.out.println("Maps are equal : " + output.equals(expectedOutput));
}
}
编辑:
得到这个问题的答案后更新了解决方案。
import java.util.HashMap;
import java.util.Map;
public class Demo {
public static void main(String[]args){
String twoHeartsStr = "";//Try #, alphabet, number etc.
Map<String, Long> output = new HashMap<>();
int codePoint = twoHeartsStr.codePointAt(0);
String charValue = String.valueOf(Character.toChars(codePoint));//Size = 2 for twoHearts.
output.put(charValue, 1L);
Map<String, Long> expectedOutput = Map.of("", 1L);
System.out.println("Maps are equal : " + output.equals(expectedOutput));//true.
}
}
The code does not work with some special symbols like "two hearts"... Why does this happen
Java char
类型是一个 16 位值。在 Unicode 的早期,这足以存储所有代码点值,但很快就改变了。已建立的 Unicode 规范允许超过一百万个字符,其中一些需要用 "surrogate pair".
表示
A String represents a string in the UTF-16 format in which supplementary characters are represented by surrogate pairs (see the section Unicode Character Representations in the Character class for more information). Index values refer to char code units, so a supplementary character uses two positions in a String.
继续:
twoHeartsStr.charAt(0)
这将为您提供代理项对的前半部分,尽管它是一个有效的 char
值,但它本身并不是一个有效字符(char
基本上是一个 integer 类型而不是文本类型)。
...and how to fix it ?
您可以使用 32 位整数(即 int
或 Integer
)来表示值,并使用 the codePointAt
method 从字符串中提取它们。但是请注意,当您遍历字符串时,您仍然需要跳过与对的后半部分对应的索引。
您仍然无法将“补充字符”存储在 char
中,因此您将无法将它们写入 char 字面值。因此,要在生成的直方图中查找双心字符(或填充用于测试的参考数据),您需要从具有该符号的字符串中获取整数代码点值。
根据Java的定义,""
不是一个字符;是两个:
>>> "".length()
2 (int)
所以''
是一个语法错误,因为char
是一个16位整数类型,而Unicode符号并不是仅仅用一个16位整数值来表示的。
您的问题的解决方案是改用字符串。
我必须计算给定字符串中的字符数。我将计数保存到地图 Map<Character, Long>
。该代码不适用于某些特殊符号,例如“两颗心”。当我将这样的特殊符号转换为字符时,会出现编译器错误“字符文字中的字符过多”或类似错误。为什么会发生这种情况以及如何解决?
这里有一些粗略的代码来演示这个问题。这不是完整代码。
import java.util.HashMap;
import java.util.Map;
public class Demo {
public static void main(String[]args){
String twoHeartsStr = "";
Map<Character, Long> output = new HashMap<>();
output.put(twoHeartsStr.charAt(0), 1L);
//Compiler error:
//intellij IDE compiler : Too many characters in character literal.
//java: unclosed character literal.
Map<Character, Long> expectedOutput = Map.of('', 1L);
System.out.println("Maps are equal : " + output.equals(expectedOutput));
}
}
编辑: 得到这个问题的答案后更新了解决方案。
import java.util.HashMap;
import java.util.Map;
public class Demo {
public static void main(String[]args){
String twoHeartsStr = "";//Try #, alphabet, number etc.
Map<String, Long> output = new HashMap<>();
int codePoint = twoHeartsStr.codePointAt(0);
String charValue = String.valueOf(Character.toChars(codePoint));//Size = 2 for twoHearts.
output.put(charValue, 1L);
Map<String, Long> expectedOutput = Map.of("", 1L);
System.out.println("Maps are equal : " + output.equals(expectedOutput));//true.
}
}
The code does not work with some special symbols like "two hearts"... Why does this happen
Java char
类型是一个 16 位值。在 Unicode 的早期,这足以存储所有代码点值,但很快就改变了。已建立的 Unicode 规范允许超过一百万个字符,其中一些需要用 "surrogate pair".
A String represents a string in the UTF-16 format in which supplementary characters are represented by surrogate pairs (see the section Unicode Character Representations in the Character class for more information). Index values refer to char code units, so a supplementary character uses two positions in a String.
继续:
twoHeartsStr.charAt(0)
这将为您提供代理项对的前半部分,尽管它是一个有效的 char
值,但它本身并不是一个有效字符(char
基本上是一个 integer 类型而不是文本类型)。
...and how to fix it ?
您可以使用 32 位整数(即 int
或 Integer
)来表示值,并使用 the codePointAt
method 从字符串中提取它们。但是请注意,当您遍历字符串时,您仍然需要跳过与对的后半部分对应的索引。
您仍然无法将“补充字符”存储在 char
中,因此您将无法将它们写入 char 字面值。因此,要在生成的直方图中查找双心字符(或填充用于测试的参考数据),您需要从具有该符号的字符串中获取整数代码点值。
根据Java的定义,""
不是一个字符;是两个:
>>> "".length()
2 (int)
所以''
是一个语法错误,因为char
是一个16位整数类型,而Unicode符号并不是仅仅用一个16位整数值来表示的。
您的问题的解决方案是改用字符串。