2009-07-31 5 views
5

Tôi đang sử dụng lớp DecimalFormat của Java để in ra các số trong Ký hiệu khoa học. Tuy nhiên, có một vấn đề mà tôi có. Tôi cần các chuỗi có chiều dài cố định bất kể giá trị, và dấu hiệu trên sức mạnh của mười là ném nó đi. Hiện tại, đây là định dạng của tôi trông giống như:Java DecimalFormat Ký hiệu khoa học Câu hỏi

DecimalFormat format = new DecimalFormat("0.0E0"); 

Điều này mang lại cho tôi các kết hợp sau: 1.0E1, 1.0E-1, -1.0E1 và -1.0E-1.

Tôi có thể sử dụng setPositivePrefix để nhận: + 1.0E1, + 1.0E-1, -1.0E1 và -1.0E-1 hoặc bất kỳ thứ gì tôi thích, nhưng nó không ảnh hưởng đến dấu hiệu của quyền lực !

Có cách nào để thực hiện việc này để tôi có thể có các chuỗi có độ dài cố định không? Cảm ơn!

Chỉnh sửa: Ah, do đó, không có cách nào để thực hiện điều đó bằng cách sử dụng API DecimalFormat hiện tại của Java? Cảm ơn các đề xuất! Tôi nghĩ rằng tôi có thể phải phân lớp DecimalFormat vì tôi bị giới hạn bởi giao diện đã có sẵn.

Trả lời

2

Đây là một cách. Kiến thức cơ bản, có lẽ, nhưng nó hoạt động ...

public class DecimalFormatTest extends TestCase { 
    private static class MyFormat extends NumberFormat { 
     private final DecimalFormat decimal; 

     public MyFormat(String pattern) { 
      decimal = new DecimalFormat(pattern); 
     } 

     public StringBuffer format(double number, StringBuffer toAppendTo, FieldPosition pos) { 
      StringBuffer sb = new StringBuffer(); 
      sb.append(modified(Math.abs(number) > 1.0, decimal.format(number, toAppendTo, pos).toString())); 
      return sb; 
     } 

     private String modified(boolean large, String s) { 
      return large ? s.replace("E", "E+") : s; 
     } 

     public StringBuffer format(long number, StringBuffer toAppendTo, FieldPosition pos) { 
      StringBuffer sb = new StringBuffer(); 
      sb.append(modified(true, decimal.format(number, toAppendTo, pos).toString())); 
      return sb; 
     } 

     public Number parse(String source, ParsePosition parsePosition) { 
      return decimal.parse(source, parsePosition); 
     } 

     public void setPositivePrefix(String newValue) { 
      decimal.setPositivePrefix(newValue); 
     } 
    } 
    private MyFormat format; 

    protected void setUp() throws Exception { 
     format = new MyFormat("0.0E0"); 
     format.setPositivePrefix("+"); 
    } 

    public void testPositiveLargeNumber() throws Exception { 
     assertEquals("+1.0E+2", format.format(100.0)); 
    } 

    public void testPositiveSmallNumber() throws Exception { 
     assertEquals("+1.0E-2", format.format(0.01)); 
    } 

    public void testNegativeLargeNumber() throws Exception { 
     assertEquals("-1.0E+2", format.format(-100.0)); 
    } 

    public void testNegativeSmallNumber() throws Exception { 
     assertEquals("-1.0E-2", format.format(-0.01)); 
    } 
} 

Hoặc bạn có thể lớp con DecimalFormat, nhưng tôi thấy nó thường sạch hơn không phải phân lớp từ lớp bê tông.

2

bạn có thể sử dụng thay vì printf():

Format format = new DecimalFormat("0.0E0"); 
Double d = new Double(.01); 
System.out.println(format.format(d)); 
System.out.printf("%1.1E\n", d); 
d = new Double(100); 
System.out.println(format.format(d)); 
System.out.printf("%1.1E\n", d); 

Output:

1.0E-2 
1.0E-02 
1.0E2 
1.0E+02 

Nếu bạn cần để xuất ra một String thay vào đó, bạn có thể sử dụng những thông tin được cung cấp tại Formatted Printing for Java (sprintf) để làm điều đó.

EDIT: Wow, đó PrintfFormat() điều là rất lớn và có vẻ là không cần thiết:

OutputStream b = new ByteArrayOutputStream(); 
PrintStream p = new PrintStream(b); 
p.printf("%1.1E", d); 
System.out.println(b.toString()); 

tôi đã có ý tưởng cho đoạn code trên từ Get an OutputStream into a String.

4

này làm việc dưới hình thức tôi,

DecimalFormatSymbols SYMBOLS = DecimalFormatSymbols.getInstance(Locale.US); 

    if (value > 1 || value < -1) { 
     SYMBOLS.setExponentSeparator("e+"); 
    } else { 
     SYMBOLS.setExponentSeparator("e"); 
    } 

    DecimalFormat format = new DecimalFormat(sb.toString(), SYMBOLS); 
-1

Tại sao không sử dụng mẫu "0.0E + 0" để thay thế? Lưu ý dấu cộng trước số 0 cuối cùng.

+0

Bởi vì kết quả mô hình đề xuất trong một 'java.lang.IllegalArgumentException' chứa văn bản: _Malformed mẫu mũ "0.0E + 0" _ –

0

Cách sử dụng?
Xem phương thức formatTest.

if (value.compareTo(positive) == 1 || value.compareTo(negative) == -1) là hữu ích cho số rất lớn

/** 
* inspired by:<br> 
* https://stackoverflow.com/a/13065493/8356718 
* https://stackoverflow.com/a/18027214/8356718 
* https://stackoverflow.com/a/25794946/8356718 
*/ 
public static String format(String number, int scale) { 
    BigDecimal value = new BigDecimal(number); 
    DecimalFormatSymbols symbols = DecimalFormatSymbols.getInstance(Locale.US); 
    BigDecimal positive = new BigDecimal(1);// scale is zero 
    positive.setScale(0);// unnecessary 
    BigDecimal negative = new BigDecimal(-1);// scale is zero 
    negative.setScale(0);// unnecessary 
    if (value.compareTo(positive) == 1 || value.compareTo(negative) == -1) { 
     symbols.setExponentSeparator("e+"); 
    } else { 
     symbols.setExponentSeparator("e"); 
    } 
    DecimalFormat formatter = new DecimalFormat("0.0E0", symbols); 
    formatter.setRoundingMode(RoundingMode.HALF_UP); 
    formatter.setMinimumFractionDigits(scale); 
    return formatter.format(value); 
} 

/** 
* set the scale automatically 
*/ 
public static String format(String number) { 
    BigDecimal value = new BigDecimal(number); 
    return format(number, value.scale() > 0 ? value.precision() : value.scale()); 
} 

/* 
output: 
---------- 
0e0 
1.0e-2 
-1.0e-2 
1.234560e-5 
-1.234560e-5 
1e0 
-1e0 
3e+0 
-3e+0 
2e+2 
-2e+2 
---------- 
0.0000000000e0 
1.0000000000e-2 
-1.0000000000e-2 
1.2345600000e-5 
-1.2345600000e-5 
1.0000000000e0 
-1.0000000000e0 
3.0000000000e+0 
-3.0000000000e+0 
2.0000000000e+2 
-2.0000000000e+2 
---------- 
*/ 
public static void formatTest() { 
    System.out.println("----------"); 
    System.out.println(format("0")); 
    System.out.println(format("0.01")); 
    System.out.println(format("-0.01")); 
    System.out.println(format("0.000")); 
    System.out.println(format("-0.000")); 
    System.out.println(format("1")); 
    System.out.println(format("-1")); 
    System.out.println(format("3")); 
    System.out.println(format("-3")); 
    System.out.println(format("200")); 
    System.out.println(format("-200")); 
    System.out.println("----------"); 
    System.out.println(format("0", 10)); 
    System.out.println(format("0.01", 10)); 
    System.out.println(format("-0.01", 10)); 
    System.out.println(format("0.000", 10)); 
    System.out.println(format("-0.000", 10)); 
    System.out.println(format("1", 10)); 
    System.out.println(format("-1", 10)); 
    System.out.println(format("3", 10)); 
    System.out.println(format("-3", 10)); 
    System.out.println(format("200", 10)); 
    System.out.println(format("-200", 10)); 
    System.out.println("----------"); 
} 
+0

Hãy chỉnh sửa bạn đăng để bao gồm giải thích về cách nó trả lời câu hỏi. –