Go Web:數據存儲(1)——內存存儲

數據能夠存儲在內存中、文件中、按二進制序列化存儲的文件中、數據庫中等。html

內存存儲

將數據存儲到內存中。此處所指的內存是指應用程序自身的內存空間(如slice、array、map、struct、隊列、樹等等容器),而不是外部的內存數據庫(如redis)。linux

例如,要存儲博客文章。redis

每篇博客文章都有文章ID、文章內容以及文章做者(關於博客類文章,通常還有瀏覽量、點贊數量、評論、文章發表時間、文章是否置頂、標籤、是否轉載等等屬性)。假設它是一個struct結構:docker

type Post struct {
    Id      int
    Content string
    Author  string
}

爲了在內存中存儲每一篇Post,能夠考慮將每篇Post放進一個slice,也能夠放進map。由於id或author或content和文章之間有映射關係,使用map顯然更好一些。shell

var PostById map[int]*Post

這樣就能經過Id來檢索對應的文章,注意上面map的value是指針類型的,不建議使用值類型的,這樣會產生副本。數據庫

若是想要經過Author來檢索文章,則還能夠使用一個map來存儲這個做者下的全部文章。由於一個做者能夠有多篇文章,因此map的value應該是一個容器,好比slice。app

var PostsByAuthor map[string][]*Post

還能夠關鍵字來檢索Content從而找出關鍵字近似的文章,也就是搜索引擎類型的檢索方式。這個比較複雜一些。函數

還有一些文章設置了標籤關鍵字,好比linux類的文章,docker標籤的文章,shell標籤的文章等。爲了能夠使用標籤檢索文章,還須要建立一個按照標籤方式進行存儲文章的map容器。關於標籤的存儲方式,此處略過。post

如今假設就前面定義的兩種存儲方式:PostById和PostsByAuthor,定義提交文章的函數:搜索引擎

func store(post *Post) {
    PostById[post.Id] = post
    PostsByAuthor[post.Author] = append(PostByAutor[post.Autor], post)
}

注意,上面store()函數的參數是指針類型的。

文章存儲到上面兩種容器中後,就能夠從任意一種容器中檢索文章。由於存儲時是使用指針類型存儲的,因此不管從哪種容器中檢索獲得的文章,和另外一種方式檢索獲得的是相同的文章。

例如:

// 按文章Id檢索文章並輸出文章的Content
fmt.Println(PostById[1])
fmt.Println(PostById[2])

// 按做者檢索文章並輸出文章的Content
for _, post := range PostsByAuthor["userA"]{
    fmt.Println(post)
}

下面是完整的代碼:

package main

import (
    "fmt"
)

type Post struct {
    Id      int
    Content string
    Author  string
}

// 用於存儲的兩個內存容器
var PostById map[int]*Post
var PostsByAuthor map[string][]*Post

// 存儲數據
func store(post *Post) {
    PostById[post.Id] = post
    PostsByAuthor[post.Author] = append(PostsByAuthor[post.Author], post)
}

func main() {
    PostById = make(map[int]*Post)
    PostsByAuthor = make(map[string][]*Post)
    post1 := &Post{Id: 1, Content: "Hello 1", Author: "userA"}
    post2 := &Post{Id: 2, Content: "Hello 2", Author: "userB"}
    post3 := &Post{Id: 3, Content: "Hello 3", Author: "userC"}
    post4 := &Post{Id: 4, Content: "Hello 4", Author: "userA"}
    store(post1)
    store(post2)
    store(post3)
    store(post4)
    fmt.Println(PostById[1])
    fmt.Println(PostById[2])
    for _, post := range PostsByAuthor["userA"] {
        fmt.Println(post)
    }
    for _, post := range PostsByAuthor["userC"] {
        fmt.Println(post)
    }
}

執行結果:

&{1 Hello 1 userA}
&{2 Hello 2 userB}
&{1 Hello 1 userA}
&{4 Hello 4 userA}
&{3 Hello 3 userC}
相關文章
相關標籤/搜索