全部学科
NodeJS全栈
nodejs
Python全栈
python
小程序首页
📅 2026-05-09 6 分钟 ✍️ juanwangdev

字符串比较

字符串比较是开发中最常见的操作之一。

equals内容比较

equals比较字符串内容

Java
String s1 = "Hello";
String s2 = "Hello";
String s3 = new String("Hello");
String s4 = "World";

// equals比较内容是否相同
boolean r1 = s1.equals(s2);  // true
boolean r2 = s1.equals(s3);  // true
boolean r3 = s1.equals(s4);  // false

// equals区分大小写
String s5 = "hello";
boolean r4 = s1.equals(s5);  // false

equalsIgnoreCase忽略大小写

Java
String s1 = "Hello";
String s2 = "hello";

// equalsIgnoreCase忽略大小写比较
boolean r1 = s1.equalsIgnoreCase(s2);  // true

String s3 = "HELLO";
boolean r2 = s1.equalsIgnoreCase(s3);  // true

安全调用equals

Java
// 错误方式:null调用equals会NPE
String str = null;
// str.equals("Hello");  // NullPointerException

// 正确方式1:常量在前
boolean r = "Hello".equals(str);  // false(安全)

// 正确方式2:null检查
if (str != null && str.equals("Hello")) {
    // 处理
}

// 正确方式3:Objects.equals(Java 7+)
boolean r = Objects.equals(str, "Hello");  // false(空安全)

==引用比较

==比较引用地址

Java
String s1 = "Hello";          // 常量池
String s2 = "Hello";          // 常量池(同一对象)
String s3 = new String("Hello");  // 堆内存(新对象)

// ==比较是否同一对象(地址)
boolean r1 = s1 == s2;  // true(同一常量池对象)
boolean r2 = s1 == s3;  // false(不同对象)
boolean r3 = s2 == s3;  // false

字面量与new的区别

Java
// 字面量:常量池,相同内容共享同一对象
String a1 = "Java";
String a2 = "Java";
System.out.println(a1 == a2);  // true

// new:堆内存,每次创建新对象
String b1 = new String("Java");
String b2 = new String("Java");
System.out.println(b1 == b2);  // false

// 内容相同
System.out.println(a1.equals(b1));  // true

intern返回常量池引用

Java
String s1 = new String("Hello");
String s2 = s1.intern();  // 返回常量池引用

String s3 = "Hello";  // 常量池
System.out.println(s2 == s3);  // true

compareTo字典序比较

compareTo比较字典顺序

Java
String s1 = "Apple";
String s2 = "Banana";
String s3 = "Apple";

// 返回值:
// 0:相等
// < 0:s1在s2之前(字典序)
// > 0:s1在s2之后

int r1 = s1.compareTo(s2);  // -1(Apple < Banana)
int r2 = s2.compareTo(s1);  // 1(Banana > Apple)
int r3 = s1.compareTo(s3);  // 0(相等)

compareTo比较原理

Java
// 按字符逐个比较
"Apple".compareTo("Apricot");
// A相同,p相同,p < r → 返回负数

// 长度不同时
"App".compareTo("Apple");
// 前三个字符相同,前者短 → 返回负数

compareToIgnoreCase忽略大小写

Java
String s1 = "Apple";
String s2 = "apple";

int r1 = s1.compareTo(s2);           // 负数(区分大小写)
int r2 = s1.compareToIgnoreCase(s2); // 0(忽略大小写)

字符串排序

使用compareTo排序

Java
String[] arr = {"Banana", "Apple", "Cherry"};

Arrays.sort(arr);  // 自动使用compareTo
// 结果:["Apple", "Banana", "Cherry"]

// 手动排序
List<String> list = Arrays.asList("Banana", "Apple", "Cherry");
list.sort(String::compareTo);  // 同样效果

自定义比较器

Java
String[] arr = {"Banana", "Apple", "Cherry"};

// 按长度排序
Arrays.sort(arr, (a, b) -> a.length() - b.length());
// ["Apple", "Banana", "Cherry"](按长度5,6,6)

// 忽略大小写排序
Arrays.sort(arr, String::compareToIgnoreCase);

常量池与比较

编译期确定的字符串

Java
// 编译期确定,进入常量池
String s1 = "Hello";
String s2 = "Hel" + "lo";  // 编译期合并
System.out.println(s1 == s2);  // true

// 运行期拼接,不进常量池
String s3 = "Hel";
String s4 = s3 + "lo";  // 运行期拼接
System.out.println(s1 == s4);  // false

intern显式加入常量池

Java
String s1 = new String("Hello");
String s2 = s1.intern();  // 加入常量池

String s3 = "Hello";
System.out.println(s2 == s3);  // true(同一常量池对象)

比较方法对比

equals与==对比

方法比较内容适用场景
equals字符串内容是否相同业务逻辑比较
==是否同一对象(地址)极少使用,常量池判断
Java
// 业务比较用equals
if (input.equals("yes")) {
    // 用户输入yes
}

// ==仅用于常量池判断(不推荐日常使用)
String s1 = "Java";
String s2 = "Java";
if (s1 == s2) {
    // 常量池同一对象
}

各比较方法总结

方法作用返回值
equals()内容相等判断boolean
equalsIgnoreCase()忽略大小写相等boolean
==同一对象判断boolean
compareTo()字典序比较int(0/负/正)
compareToIgnoreCase()忽略大小写字典序int

空值安全比较

null处理

Java
String s1 = null;
String s2 = "Hello";

// 错误:null调用equals
// s1.equals(s2);  // NullPointerException

// 正确方式1:常量在前
boolean r = "Hello".equals(s1);  // false

// 正确方式2:Objects.equals
boolean r2 = Objects.equals(s1, s2);  // false

// 正确方式3:StringUtils(Apache Commons)
boolean r3 = StringUtils.equals(s1, s2);  // false

比较最佳实践

内容比较用equals

Java
// 推荐:equals比较内容
String input = getUserInput();
if ("yes".equals(input)) {
    // 安全,即使input为null
}

// 不推荐:==比较地址
if (input == "yes") {  // 可能失败
    // 即使内容相同,可能不是同一对象
}

大小写不敏感比较

Java
String input = "YES";

// 使用equalsIgnoreCase
if ("yes".equalsIgnoreCase(input)) {
    // 匹配YES、yes、Yes等
}

多条件比较

Java
String input = "quit";

// 多值判断
if ("quit".equals(input) || "exit".equals(input) || "q".equals(input)) {
    // 退出
}

// 使用contains(List)
List<String> exits = Arrays.asList("quit", "exit", "q");
if (exits.contains(input)) {
    // 退出
}

要点总结

  • equals()比较字符串内容是否相同
  • equalsIgnoreCase()忽略大小写比较
  • ==比较是否同一对象(引用地址)
  • 字面量相同内容共享常量池对象
  • new创建的对象不共享常量池
  • compareTo()字典序比较,返回0/负/正
  • compareToIgnoreCase()忽略大小写字典序
  • 常量在前调用equals避免NPE
  • Objects.equals()空安全比较
  • intern()返回常量池引用
  • 业务比较使用equals,不用==
  • 字符串排序使用compareTo

📝 发现内容有误?点击此处直接编辑

← 上一篇 字符串拼接与性能
下一篇 → 正则表达式与字符串
想查看更多题目和详细解析?
小程序提供完整的题库、模拟考试和详细解析
马上就来

长按或扫描二维码,立即体验

扫码体验小程序
马上就来
使用微信扫描二维码
立即体验完整题库