golang 讀取JSON檔案(讀書筆記)

來源:互聯網
上載者:User
這是一個建立於 的文章,其中的資訊可能已經有所發展或是發生改變。

          JSON(JavaScript Object Notation)是一種比XML更輕量級的資料交換格式,在易於人們閱讀和編寫的同時,也易於程式解析和產生。儘管JSON是JavaScript的一個子集,但JSON採用完全獨立於程式設計語言的文字格式設定,且表現為key/value的文本描述形式(與GO語言中的map極為相似),這使它成為較理想的、跨平台的、跨語言的資料交換語言。記得初次接觸JSON這種資料形式是在剛工作時,當時在js頁面中處理非常方便,印象一直很深刻。後來,學習了一些mongodb,完全處理這種格式的資料。原來,個人很不喜歡像這種鍵-值對的資料形式,因為總覺得這個底層可能映射起來比較方便,不過,好多情況下確實是少不了這種形式。

    Go語言內建對JSON的支援,使用GO語言內建的encoding/json標準庫,開發人員可以便於使用GO程式產生和解析JSON格式的資料。


舉個例子:

package mainimport (    "encoding/json"    "fmt")type Book struct {    Title       string    Author      []string    Publisher   string    Price       float64    IsPublished bool}func main() {    b := []byte(`{    "Title":"go programming language",    "Author":["john","ada","alice"],    "Publisher":"qinghua",    "IsPublished":true,    "Price":99  }`)//先建立一個目標類型的執行個體對象,用於存放解碼後的值    var book Book    err := json.Unmarshal(b, &book)    if err != nil {        fmt.Println("error in translating,", err.Error())        return    }    fmt.Println(book.Author)}

Json.Unmarshal()函數會根據一個約定的順序尋找目標結構中的欄位,如果找到一個則進行匹配。這些欄位在型別宣告中必須都是以大寫字母開頭、可被匯出的欄位。

但是當JSON資料中的資料結構和GO中的目標類型不符時,會怎樣呢?如果JSON中的欄位在GO目標類型中不存在,json.Unmarshal()函數在解碼過程中會丟棄該欄位。這個特性讓我們可以從一段JSON資料中篩選出指定的值填充到多個GO語言類型中,當然,前提是已知JSON資料的欄位結構。這也意味著,目標類型中不可被匯出的私人欄位(非首字母大寫)將不會受到解析轉化的影響,

如果要解析一個設定檔,為了使程式端的改動能夠靈活,大多數情況下是不知道設定檔中到底是怎樣的結構,只是在需要的時候去取就可以了。GO語言支援介面。在go中,介面是一組預定義方法的組合,任何一個類型均可通過實現介面預定義的方法來實現,且無需顯示聲明,所以沒有任何方法的空介面代表任何類型。換句話說,每一個類型其實都至少實現了一個空介面。GO內建這樣靈活的類型系統,向我們傳達了一個很有價值的資訊:空介面是通用類型。如果要解析一段未知結構的JSON,只需向這段JSON資料解碼輸出到一個空介面即可。在GO的標準庫encoding/json包中,允許使用map[string]interface{}和[]interface{}類型的值來分別存放未知結構的JSON對象或數組。

還是剛才的例子,只是將結構體去掉,變成一個未知結構的資料。

package mainimport (    "encoding/json"    "fmt")func main() {    b := []byte(`{    "Title":"go programming language",    "Author":["john","ada","alice"],    "Publisher":"qinghua",    "IsPublished":true,    "Price":99  }`)    //先建立一個目標類型的執行個體對象,用於存放解碼後的值    var inter interface{}    err := json.Unmarshal(b, &inter)    if err != nil {        fmt.Println("error in translating,", err.Error())        return    }    //要訪問解碼後的資料結構,需要先判斷目標結構是否為預期的資料類型    book, ok := inter.(map[string]interface{})    //然後通過for迴圈一一訪問解碼後的目標資料    if ok {        for k, v := range book {            switch vt := v.(type) {            case float64:                fmt.Println(k, " is float64 ", vt)            case string:                fmt.Println(k, " is string ", vt)            case []interface{}:                fmt.Println(k, " is an array:")                for i, iv := range vt {                    fmt.Println(i, iv)                }            default:                fmt.Println("illegle type")            }        }    }}

說實話,這樣轉化確實很繁瑣,但也是解析未知結構的JSON資料的方式。

原來試圖使用XML來做設定檔,但是,那樣的話必須要知道有哪些資料項目(Key),而對於靈活的設定檔來說,到底包括哪些是沒有辦法提前預知的,而各個模組需要哪些資料的時候只需到公用資訊中去提取就好了,主程式也不需要知道到底有哪些資訊是公用的,它只要負責將訊息以索引值對的形式儲存起來供子程式調用就可以了。



聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.