2014-09-19 42 views
0

我在旅途中的結構:爲什麼這兩個結構不相等?

type header struct { 
    dataLength uint16 
    optDataLength uint8 
    packetType uint8 
} 
type packet struct { 
     syncByte uint8 
     header *header 
     headerCrc uint8 
     data  []byte 
     optData []byte 
     dataCrc uint8 
} 

如果我已經創建了一個編碼和解碼功能,用於創建包,併爲它們編碼成二進制。但是,爲什麼這兩個instance.header有所不同?

&{syncByte:85 header:0xc2080004b8 headerCrc:112 data:[2] optData:[] dataCrc:14} 
&{syncByte:85 header:0xc2080004f8 headerCrc:112 data:[2] optData:[] dataCrc:14} 

如果我在那兩個頭的運行的println我得到:

&{dataLength:1 optDataLength:0 packetType:5} 
&{dataLength:1 optDataLength:0 packetType:5} 

其中眉似乎相等。但爲什麼他們看起來像0xc2080004f8 vs 0xc2080004b8,當我直接檢查packet.header時看不到差異?

+0

請指定如何創建實例,是否通過引用傳遞值? – 2014-09-19 20:31:50

回答

2

它們不相等,因爲它比較指針而不是指針的值。 你有幾個選擇。

  1. 不要使用指針,你將無法在任何結構中使用片,你可以使用固定大小的數組。
  2. 編寫您自己的func (p *packet) Equals(o *packet) bool並自己比較一下。
  3. 使用reflect.DeepEqual,這是迄今爲止最慢/效率最低的解決方案,我個人會選擇#2。

簡單實現的#2:

func (h *header) Equal(o *header) bool { 
    return h != nil && o != nil && 
     h.dataLength == o.dataLength && 
     h.optDataLength == o.optDataLength && 
     h.packetType == o.packetType 
} 

func (p *packet) Equal(o *packet) bool { 
    return p != nil && o != nil && 
     p.header.Equal(o.header) && 
     p.syncByte == o.syncByte && 
     p.headerCrc == o.headerCrc && 
     p.dataCrc == o.dataCrc && 
     bytes.Equal(p.data, o.data) && 
     bytes.Equal(p.optData, o.optData) 
} 

playground

1

Decode每次調用分配header類型的新價值。您正在觀察這些已分配標頭的不同地址。兩個標頭值具有相同的內容,但是它們位於不同的地址。

+0

我也這麼認爲,但我認爲主要的問題是他比較數據包的兩個指針,而不是頭部,比較'* p1 == * p2'會因爲片的使用而失敗,用數組替換片修復,但它仍然會因爲頭指針而失敗。 – OneOfOne 2014-09-19 21:29:39

相關問題