Java經常使用類-比較器、System、Math 、BigInteger和BigDecimal

比較器

Java中有一些比較運算符,如 >、<、==、!=、>=、<=、instanceof、equals ,不過其中大部分只能比較基本數據類型,引用數據類型除了==instanceofequals以外,><這些都不能用。
因此,爲了知足對象排序的需求,java提供了兩個接口實現對象排序。java

Java實現對象排序的方式有兩種:git

  • 天然排序:java.lang.Comparable
  • 定製排序:java.util.Comparator

天然排序 Comparable接口

首先,看一下Comarable的典型例子,String類的比較。像String類或者包裝類中都實現了Comparable接口,重寫了compareTo()方法,在重寫的方法體中給出了比較兩個對象大小的方式。
如,String類中的compareTo方法中是按照字符串中字符的Unicode值進行從小到大的比較。算法

@Test
public void testComparable(){
    String[] arr = new String[]{"EE","FF","CC","BB","DD","AA"};
    Arrays.sort(arr);
    System.out.println(Arrays.toString(arr)); // 打印:[AA, BB, CC, DD, EE, FF]
}

對於天然排序來講,重寫compareTo(obj)方法的規則以下:編程

  • 若是當前對象this大於形參對象obj,則返回正整數,
  • 若是當前對象this小於形參對象obj,則返回負整數
  • 若是當前對象this等於形參對象obj,則返回零。

對於自定義類,若是須要排序,那麼可讓自定義類實現Comparable接口,並重寫CompareTo方法在CompareTo中,指明如何對對象進行排序。數組

下面進行舉例:
假如,有一個商品類,有商品價格和商品名稱的屬性,如今須要根據商品的價格高低對多個對象進行排序。數據結構

public class Goods implements Comparable{
    private String name; // 商品名稱
    private double price; // 商品價格

    public Goods() {
    }

    public Goods(String name, double price) {
        this.name = name;
        this.price = price;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public double getPrice() {
        return price;
    }

    public void setPrice(double price) {
        this.price = price;
    }
    // 重寫toString方法
    @Override
    public String toString() {
        return "name:"+ name + ",price:"+ price;
    }

    // 指明如何進行排序,好比按照商品的價格從低到高進行排序
    @Override
    public int compareTo(Object o) {
        if (o instanceof Goods){
            Goods goods = (Goods)o;
            if(this.price > goods.price){
                return 1;
            }else if(this.price < goods.price){
                return -1;
            }else{
                return 0;
            }
        }
        throw new RuntimeException("傳入的數據類型不一致!");
    }
}

測試,建立Goods對象數組,存儲四個商品,而後使用Arrays.sort進行排序,再進行輸出,代碼以下:dom

@Test
    public void testGoods(){
        Goods[] arr = new Goods[4];
        arr[0] = new Goods("Rapoo",189.9);
        arr[1] = new Goods("Logitech",239.5);
        arr[2] = new Goods("Razer",100.5);
        arr[3] = new Goods("Dell",79.9);

        System.out.println("排序前: " + Arrays.toString(arr));
        Arrays.sort(arr);
        System.out.println("排序後: " + Arrays.toString(arr));
    }

運行結果:ide

排序前: [name:Rapoo,price:189.9, name:Logitech,price:239.5, name:Razer,price:100.5, name:Dell,price:79.9]
排序後: [name:Dell,price:79.9, name:Razer,price:100.5, name:Rapoo,price:189.9, name:Logitech,price:239.5]

這樣,輸出的對象數組就會按照商品的價格從低到高進行排序。
總結一下:使用天然排序來比較自定義類的對象大小,先讓自定義實現Comparable接口,而後重寫compareTo()方法,在方法體內寫具體要根據什麼邏輯來比較對象的大小。函數

定製排序 Comparator接口

當元素的類型沒有實現java.lang.Comparable接口而又不方便修改代碼,或者實現java.lang.Comparable接口的排序規則不適合當前的操做,那麼能夠考慮使用Comparator的對象來排序,強行對多個對象進行總體排序的比較。測試

一樣,實現類須要重寫接口的方法compare(),compare方法的重寫規則以下:
對於方法compare(Object o1,Object o2),比較o1和o2的大小:

  • 若是方法返示回正整數,則表示o1大於o2 ;
  • 若是返回0,表示相等;
  • 返回負整數,表示o1 小於o2。

示例,仍是使用上面Goods.class代碼爲例:

@Test
    public void testGoods2(){
        Goods[] arr = new Goods[4];
        arr[0] = new Goods("Rapoo",189.9);
        arr[1] = new Goods("Logitech",239.5);
        arr[2] = new Goods("Razer",100.5);
        arr[3] = new Goods("Dell",79.9);

        Arrays.sort(arr, new Comparator() {
            // 指明商品比較大小的方式:按照商品名稱從低到高排序,若是是相同價格的就按照價格從高到低排序
            @Override
            public int compare(Object o, Object t1) {
                if (o instanceof Goods && t1 instanceof Goods){
                    Goods g1 = (Goods)o;
                    Goods g2 = (Goods)t1;
                    if (g1.getName().equals(g2.getName())){
                        return -Double.compare(g1.getPrice(),g2.getPrice());
                    }else{
                        return g1.getName().compareTo(g2.getName());
                    }
                }
                throw new RuntimeException("輸入的數據類型不一致");
            }
        });

        System.out.println(Arrays.toString(arr));
    }

除此以外,能夠將 Comparator 傳遞給 sort 方法(如 Collections.sort 或 Arrays.sort),從而容許在排序順序上實現精確控制。
示例:

@Test
public void testComparator(){
    String[] arr = new String[]{"EE","FF","CC","BB","DD","AA"};
    Arrays.sort(arr,new Comparator(){
    // 定製規則,讓字符串從大到小進行排序
    @Override
    public int compare(Object o, Object t1) {
        if (o instanceof String && t1 instanceof String){
            String s1 = (String)o;
            String s2 = (String)t1;
            return -s1.compareTo(s2);
            }
            throw new RuntimeException("輸入的數據類型不一致");
        }
    });
    System.out.println(Arrays.toString(arr));
}

還可使用 Comparator 來控制某些數據結構(若有序 set或有序映射)的
順序,或者爲那些沒有天然順序的對象 collection 提供排序。

經常使用類之System類

System類表明系統,系統級的不少屬性和控制方法都放置在該類的內部。該類位於java.lang包。
因爲該類的構造器是private的,因此沒法建立該類的對象,也就是沒法實例化該類。其內部的成員變量和成員方法都是static的,因此也能夠很方便的進行調用。

成員變量
System類內部包含in、out和err三個成員變量,分別表明標準輸入流(鍵盤輸入)標準輸出流(顯示器)標準錯誤輸出流(顯示器)。

成員方法
native long currentTimeMillis(): :
該方法的做用是返回當前的計算機時間,時間的表達格式爲當前計算機時間和GMT時間(格林威治時間)1970年1月1號0時0分0秒所差的毫秒數。

void exit(int status)
該方法的做用是退出程序。其中status的值爲0表明正常退出,非零表明異常退出。 使用該方法能夠在圖形界面編程中實現程序的退出功能等。

void gc()
該方法的做用是請求系統進行垃圾回收。至於系統是否馬上回收,則取決於系統中垃圾回收算法的實現以及系統執行時的狀況。
String getProperty(String key)
該方法的做用是得到系統中屬性名爲key的屬性對應的值。系統中常見的屬性名以及屬性的做用以下表所示:

屬性名 說明
java.version Java運行環境的版本
java.home Java安裝目錄
os.name 操做系統名稱
os.version 操做系統版本
user.name 用戶名稱
user.home 用戶的主目錄
user.dir 用戶當前工做目錄

示例:

@Test
    public void testSystem(){
        String javaVersion = System.getProperty("java.version");
        System.out.println("java的version:" + javaVersion);

        String javaHome = System.getProperty("java.home");
        System.out.println("java的home:" + javaHome);

        String osName = System.getProperty("os.name");
        System.out.println("os的name:" + osName);

        String osVersion = System.getProperty("os.version");
        System.out.println("os的version:" + osVersion);

        String userName = System.getProperty("user.name");
        System.out.println("user的name:" + userName);

        String userHome = System.getProperty("user.home");
        System.out.println("user的home:" + userHome);

        String userDir = System.getProperty("user.dir");
        System.out.println("user的dir:" + userDir);
    }

經常使用類之Math類

java.lang.Math提供了一系列靜態方法用於科學計算。其方法的參數和返回值類型通常爲double類型。經常使用方法以下:

  • abs:求絕對值
  • acos,asin,atan,cos,sin,tan:三角函數
  • sqrt:求平方根
  • pow(double a,doble b):求a的b次冪
  • log:求天然對數
  • exp:e爲底指數
  • max(double a,double b):求a,b的最大值
  • min(double a,double b):求a,b的最小值
  • random():返回0.0 到1.0 的隨機數
  • long round(double a) :double型數據a 轉換爲long 型(四捨五入)
  • toDegrees(double angrad):弧度—> 角度
  • toRadians(double angdeg) :角度—> 弧度

經常使用類之BigInteger類和BigDecimal類

BigInteger類

Integer類做爲int的包裝類,能存儲的最大整型值爲2^31 -1,Long類也是有限的,最大爲2^63 -1。若是要表示再大的整數,不論是基本數據類型仍是他們的包裝類都無能爲力,更不用說進行運算了。

java.math包的BigInteger能夠表示不可變的任意精度的整數BigInteger提供全部Java的基本整數操做符的對應物,並提供java.lang.Math的全部相關方法。另外,BigInteger 還提供如下運算:模算術、GCD 計算、質數測試、素數生成、位操做以及一些其餘操做。

BigDecimal類

通常的Float類和Double類能夠用來作科學計算或工程計算,但在 商業計算中,到 要求數字精度比較高,故用到java.math.BigDecimal類。
BigDecimal類支持不可變的、任意精度的有符號十進制定點數。
構造器

  • public BigDecimal(double val)
  • public BigDecimal(String val)

經常使用方法

  • public BigDecimal add(BigDecimal augend)
  • public BigDecimal subtract(BigDecimal subtrahend)
  • public BigDecimal multiply(BigDecimal multiplicand)
  • public BigDecimal divide(BigDecimal divisor, int scale, int roundingMode)
相關文章
相關標籤/搜索