golang小程式實驗(五)

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

1. golang的指標

可以將unsafe.Pointer轉換成uintptr,然後變相做指標運算

package mainimport "fmt"import "unsafe"type User struct {Id   intName string}func main() {u := &User{1, "tom"}var up uintptr = uintptr(unsafe.Pointer(u)) + unsafe.Offsetof(u.Name)var name *string = (*string)(unsafe.Pointer(up))fmt.Println(*name)}

2. package io

實現了io.Reader或io.Writer介面的類型(匯出的類型):

  • os.File 同時實現了io.Reader和io.Writer
  • strings.Reader 實現了io.Reader
  • bufio.Reader/Writer 分別實現了io.Reader和io.Writer
  • bytes.Buffer 同時實現了io.Reader和io.Writer
  • bytes.Reader 實現了io.Reader
  • compress/gzip.Reader/Writer 分別實現了io.Reader和io.Writer
  • crypto/cipher.StreamReader/StreamWriter 分別實現了io.Reader和io.Writer
  • crypto/tls.Conn 同時實現了io.Reader和io.Writer
  • encoding/csv.Reader/Writer 分別實現了io.Reader和io.Writer
  • mime/multipart.Part 實現了io.Reader
以上類型中,常用的類型有:os.File、strings.Reader、bufio.Reader/Writer、bytes.Buffer、bytes.Reader

WriteAt()方法簡單樣本:

file, err := os.Create("writeAt.txt")if err != nil {    panic(err)}defer file.Close()file.WriteString("Golang中文社區——這裡是多餘的")n, err := file.WriteAt([]byte("Go語言學習園地"), 24)if err != nil {    panic(err)}fmt.Println(n)

file.WriteString("Golang中文社區——這裡是多餘的") 往檔案中寫入Golang中文社區——這裡是多餘的;之後file.WriteAt([]byte("Go語言學習園地"), 24) 在檔案流的offset=24處寫入Go語言學習園地(會覆蓋該位置的內容)。

ReadFrom()方法簡單樣本:

file, err := os.Open("writeAt.txt")if err != nil {    panic(err)}defer file.Close()writer := bufio.NewWriter(os.Stdout)writer.ReadFrom(file)writer.Flush()
WriteTo()方法樣本:
reader := bytes.NewReader([]byte("Go語言學習園地"))reader.WriteTo(os.Stdout)
Seek()方法樣本:
reader := strings.NewReader("Go語言學習園地")reader.Seek(-6, os.SEEK_END)r, _, _ := reader.ReadRune()fmt.Printf("%c\n", r)

在標準庫中,有如下類型實現了io.ByteReader或io.ByteWriter:

  • bufio.Reader/Writer 分別實現了io.ByteReader和io.ByteWriter
  • bytes.Buffer 同時實現了io.ByteReader和io.ByteWriter
  • bytes.Reader 實現了io.ByteReader
  • strings.Reader 實現了io.ByteReader

接下來的樣本中,我們通過bytes.Buffer來一次讀取或寫入一個位元組(主要代碼):

var ch bytefmt.Scanf("%c\n", &ch)buffer := new(bytes.Buffer)err := buffer.WriteByte(ch)if err == nil {    fmt.Println("寫入一個位元組成功!準備讀取該位元組……")    newCh, _ := buffer.ReadByte()    fmt.Printf("讀取的位元組:%c\n", newCh)} else {    fmt.Println("寫入錯誤")}
Pipe()方法和PipeReader、PipeWriter結構的樣本:
func main() {    Pipe()}func Pipe() {    pipeReader, pipeWriter := io.Pipe()    go PipeWrite(pipeWriter)    go PipeRead(pipeReader)    time.Sleep(1e7)}func PipeWrite(pipeWriter *io.PipeWriter) {    var (        i   = 0        err error        n int    )    data := []byte("Go語言學習園地")    for _, err = pipeWriter.Write(data); err == nil; n, err = pipeWriter.Write(data) {        i++        if i == 3 {            pipeWriter.CloseWithError(errors.New("輸出3次後結束"))        }    }    fmt.Println("close 後輸出的位元組數:", n, " error:",  err)}func PipeRead(pipeReader *io.PipeReader) {    var (        err error        n   int    )    data := make([]byte, 1024)    for n, err = pipeReader.Read(data); err == nil; n, err = pipeReader.Read(data) {        fmt.Printf("%s\n", data[:n])    }    fmt.Println("writer 端 closewitherror後:", err)}
Copy()方法樣本:
package mainimport (    "fmt"    "io"    "os")func main() {    io.Copy(os.Stdout, strings.NewReader("Go語言學習園地"))    io.Copy(os.Stdout, os.Stdin)    fmt.Println("Got EOF -- bye")}

3. 程式結構

假設有一個服務的大致實現是這樣的:

type Service struct {wg sync.WaitGroup}func (p *Service) Start() {p.wg.Add(1)go p.run()}func (p *Service) Close() {// ...p.wg.Wait()}func (p *Service) run() {defer p.wg.Done()// ....}
其中run()是服務的主要邏輯實現。這樣寫法的問題是wg的Add和Done函數調用分離了,容易導致在以後的代碼維護中不小心就導致Add和Done的調用不匹配從而Wait執行的結果不符合預期。從程式碼群組織的方式上來說,應該把功能相關的代碼儘可能地放在一起。

type Service struct {wg sync.WaitGroup}func (p *Service) Start() {p.wg.Add(1)go func() {p.run()p.wg.Done()}()}func (p *Service) Close() {// ...p.wg.Wait()}func (p *Service) run() {// ....}
這個其實也算常識了,寫過些代碼的人可能都知道。但是在實際的代碼中,我們往往還會發現類似這樣的一些不好的寫法。因此,對於這些慣用法(或者升級為代碼規範),我覺得更重要的不是瞭解知道,而是執行和遵守。
相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在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.