选择哪种方法?
| 方法 | 优点 | 缺点 | 推荐场景 |
|---|---|---|---|
String.valueOf(double d) |
简单、直接,是官方推荐的“标准”方式。 | 对于科学计数法或需要精确控制格式的场景不够灵活。 | 通用转换,不关心具体格式时。 |
Double.toString(double d) |
与 String.valueOf 在底层实现上几乎完全相同。 |
同上。 | 与 Double 类相关的操作时,或者个人偏好。 |
"" + double (字符串拼接) |
代码最简洁。 | 性能略低,且意图不如前两者明确(可能被误认为是字符串拼接)。 | 快速、临时的转换,代码量少。 |
String.format() |
功能最强大,可以精确控制格式(小数位数、科学计数法、千位分隔符等)。 | 语法相对复杂一些。 | 需要格式化输出,如显示固定小数位、货币、百分比等。 |
DecimalFormat |
功能强大,专门用于数字格式化,支持复杂的本地化模式。 | 需要创建对象,比 String.format 稍显繁琐。 |
需要重复使用同一格式模式,或进行复杂的本地化数字格式化。 |
String.valueOf(double d) - 最推荐的标准方法
这是最常用、最直接的方法,它是一个静态方法,直接将 double 参数转换为其字符串表示形式。

特点:
- 简单明了。
- 处理
Double.NaN和Double.INFINITY等特殊情况,会返回字符串"NaN"和"Infinity"。 - 性能良好。
示例代码:
public class DoubleToStringExample {
public static void main(String[] args) {
double number = 123.456;
// 标准转换
String str1 = String.valueOf(number);
System.out.println("String.valueOf: " + str1); // 输出: String.valueOf: 123.456
// 处理特殊值
double nan = Double.NaN;
double infinity = Double.POSITIVE_INFINITY;
System.out.println("NaN: " + String.valueOf(nan)); // 输出: NaN: NaN
System.out.println("Infinity: " + String.valueOf(infinity)); // 输出: Infinity: Infinity
}
}
Double.toString(double d)
这是 Double 类中的一个静态方法,作用与 String.valueOf(double) 非常相似。
特点:
- 功能与
String.valueOf基本一致。 - 在 Java 源码中,
String.valueOf(double)内部就是调用了Double.toString(double)。 - 同样能正确处理
NaN和Infinity。
示例代码:

public class DoubleToStringExample {
public static void main(String[] args) {
double number = 789.012;
String str2 = Double.toString(number);
System.out.println("Double.toString: " + str2); // 输出: Double.toString: 789.012
}
}
使用空字符串拼接 "" + double
这是一种非常简洁的语法糖,利用了 Java 的字符串自动转换机制。
特点:
- 代码最短。
- 性能稍差:JVM 在处理 运算符时,可能会在内部创建一个
StringBuilder对象,虽然现代 JVM 优化得很好,但理论上性能不如直接调用String.valueOf。 - 可读性稍差,可能不如前两种方法清晰。
示例代码:
public class DoubleToStringExample {
public static void main(String[] args) {
double number = 3.14159;
String str3 = "" + number;
System.out.println("String Concatenation: " + str3); // 输出: String Concatenation: 3.14159
}
}
String.format() - 强大的格式化工具
当你需要控制 double 转换为 String 的具体格式时,String.format() 是最佳选择,它使用格式说明符来定义输出格式。
常用格式说明符:

%f: 默认格式,输出浮点数。%.nf: 保留 n 位小数。%e或%E: 使用科学计数法。%g或%G: 根据数值大小自动选择%f或%e。- : 添加千位分隔符。
示例代码:
public class DoubleToStringFormatExample {
public static void main(String[] args) {
double price = 1234567.8912;
// 1. 默认格式
System.out.println("默认格式: " + String.format("%f", price));
// 输出: 默认格式: 1234567.891200 (默认保留6位小数)
// 2. 保留2位小数 (常用)
System.out.println("保留2位小数: " + String.format("%.2f", price));
// 输出: 保留2位小数: 1234567.89
// 3. 保留4位小数,并进行四舍五入
System.out.println("保留4位小数: " + String.format("%.4f", price));
// 输出: 保留4位小数: 1234567.8912
// 4. 使用千位分隔符
System.out.println("千位分隔符: " + String.format("%,.2f", price));
// 输出: 千位分隔符: 1,234,567.89
// 5. 使用科学计数法
System.out.println("科学计数法: " + String.format("%e", price));
// 输出: 科学计数法: 1.234568e+06
// 6. 格式化为货币样式 (需要本地化,这里简单示例)
System.out.println("货币样式: $" + String.format("%,.2f", price));
// 输出: 货币样式: $1,234,567.89
}
}
java.text.DecimalFormat - 专业的数字格式化
DecimalFormat 是一个更专业的格式化工具,它允许你定义一个模式字符串,然后根据这个模式来格式化数字,特别适合在需要重复应用同一格式的场景。
特点:
- 功能非常强大和灵活。
- 支持复杂的本地化模式(不同地区的数字、货币、日期格式不同)。
- 需要先创建
DecimalFormat对象。
示例代码:
import java.text.DecimalFormat;
public class DoubleToStringDecimalFormatExample {
public static void main(String[] args) {
double number = 9876543.21;
// 1. 创建模式 "#,###.##" 表示整数部分用逗号分隔,保留两位小数
DecimalFormat df1 = new DecimalFormat("#,###.##");
System.out.println("千位分隔+2位小数: " + df1.format(number));
// 输出: 千位分隔+2位小数: 9,876,543.21
// 2. 创建模式 "0.00" 表示保留两位小数,不足补0
DecimalFormat df2 = new DecimalFormat("0.00");
System.out.println("保留2位小数(补0): " + df2.format(123.4));
// 输出: 保留2位小数(补0): 123.40
// 3. 创建模式 "0.00%" 表示将数字乘以100,并添加百分号
DecimalFormat df3 = new DecimalFormat("0.00%");
System.out.println("百分比格式: " + df3.format(0.1234));
// 输出: 百分比格式: 12.34%
}
}
⚠️ 重要注意事项:浮点数精度问题
double 是一种二进制浮点数,它无法精确表示某些十进制小数(如 0.1),在进行转换时,可能会出现意外的精度问题。
问题示例:
double badDouble = 123.45678901234567; // 这个 double 本身就可能已经丢失了精度
System.out.println(badDouble); // 输出可能是 123.45678901234568
// 当你期望它精确到 15 位小数时
System.out.println(String.format("%.15f", badDouble));
// 输
