如何定义Golang结构体以解析指定XML数据?
解决方案:Go中XML反序列化的结构体定义
嘿,这个问题我熟!咱们一步步来搞定Go里这个XML的反序列化,先分析你的XML结构,再定义对应的结构体,最后给你个完整的可运行示例。
首先拆解你的XML结构:
- 根节点是
<ZIP_result>,包含多个独立的<result>元素(每个元素只有一个专属属性),以及一个<ADDRESS_value>节点,后者又包含多个带单一属性的<value>元素。
1. 定义单个<result>元素的结构体
每个<result>元素只有一个属性,我们把所有可能的属性都定义在结构体里,用omitempty忽略空值,这样反序列化时只会填充对应存在的属性:
type Result struct { Name string `xml:"name,attr,omitempty"` Version string `xml:"version,attr,omitempty"` RequestURL string `xml:"request_url,attr,omitempty"` RequestZipNum string `xml:"request_zip_num,attr,omitempty"` RequestZipVersion string `xml:"request_zip_version,attr,omitempty"` ResultCode string `xml:"result_code,attr,omitempty"` ResultZipNum string `xml:"result_zip_num,attr,omitempty"` ResultZipVersion string `xml:"result_zip_version,attr,omitempty"` ResultValuesCount string `xml:"result_values_count,attr,omitempty"` }
注:如果某些属性是数字类型(比如
result_code),可以把字段类型改成int,但用string更稳妥,避免XML里出现非数字值导致解析错误。
2. 定义<ADDRESS_value>节点的结构体
<ADDRESS_value>下的每个<value>元素对应一个地址属性,我们用xml:"value>属性名,attr"的标签来匹配每个<value>元素的属性:
type AddressValue struct { StateKana string `xml:"value>state_kana,attr"` CityKana string `xml:"value>city_kana,attr"` AddressKana string `xml:"value>address_kana,attr"` CompanyKana string `xml:"value>company_kana,attr"` State string `xml:"value>state,attr"` City string `xml:"value>city,attr"` Address string `xml:"value>address,attr"` Company string `xml:"value>company,attr"` }
3. 定义根节点<ZIP_result>的结构体
把上面两个结构体组合起来,同时指定根节点的名称,确保反序列化时精准匹配:
type ZIPResult struct { XMLName xml.Name `xml:"ZIP_result"` Results []Result `xml:"result"` AddressVal AddressValue `xml:"ADDRESS_value"` }
完整示例代码
下面是一个可直接运行的示例,展示如何反序列化你的XML:
package main import ( "encoding/xml" "fmt" ) type Result struct { Name string `xml:"name,attr,omitempty"` Version string `xml:"version,attr,omitempty"` RequestURL string `xml:"request_url,attr,omitempty"` RequestZipNum string `xml:"request_zip_num,attr,omitempty"` RequestZipVersion string `xml:"request_zip_version,attr,omitempty"` ResultCode string `xml:"result_code,attr,omitempty"` ResultZipNum string `xml:"result_zip_num,attr,omitempty"` ResultZipVersion string `xml:"result_zip_version,attr,omitempty"` ResultValuesCount string `xml:"result_values_count,attr,omitempty"` } type AddressValue struct { StateKana string `xml:"value>state_kana,attr"` CityKana string `xml:"value>city_kana,attr"` AddressKana string `xml:"value>address_kana,attr"` CompanyKana string `xml:"value>company_kana,attr"` State string `xml:"value>state,attr"` City string `xml:"value>city,attr"` Address string `xml:"value>address,attr"` Company string `xml:"value>company,attr"` } type ZIPResult struct { XMLName xml.Name `xml:"ZIP_result"` Results []Result `xml:"result"` AddressVal AddressValue `xml:"ADDRESS_value"` } func main() { // 你的XML数据 xmlData := `<ZIP_result> <result name="ZipSearchXML"/> <result version="1.01"/> <result request_url="http%3A%2F%2Fzip.cgis.biz%2Fxml%2Fzip.php%3Fzn%3D1310045"/> <result request_zip_num="1310045"/> <result request_zip_version="none"/> <result result_code="1"/> <result result_zip_num="1310045"/> <result result_zip_version="0"/> <result result_values_count="1"/> <ADDRESS_value> <value state_kana="トウキョウト"/> <value city_kana="スミダク"/> <value address_kana="オシアゲ"/> <value company_kana="none"/> <value state="東京都"/> <value city="墨田区"/> <value address="押上"/> <value company="none"/> </ADDRESS_value> </ZIP_result>` var zipRes ZIPResult err := xml.Unmarshal([]byte(xmlData), &zipRes) if err != nil { fmt.Printf("解析XML出错: %v\n", err) return } // 打印解析结果 fmt.Println("=== 基础查询结果 ===") for _, res := range zipRes.Results { if res.Name != "" { fmt.Printf("接口名称: %s\n", res.Name) } if res.Version != "" { fmt.Printf("接口版本: %s\n", res.Version) } if res.RequestZipNum != "" { fmt.Printf("请求的邮编: %s\n", res.RequestZipNum) } if res.ResultCode != "" { fmt.Printf("结果码: %s\n", res.ResultCode) } } fmt.Println("\n=== 地址信息 ===") fmt.Printf("假名都道府县: %s\n", zipRes.AddressVal.StateKana) fmt.Printf("假名市区町村: %s\n", zipRes.AddressVal.CityKana) fmt.Printf("假名町域: %s\n", zipRes.AddressVal.AddressKana) fmt.Printf("都道府县: %s\n", zipRes.AddressVal.State) fmt.Printf("市区町村: %s\n", zipRes.AddressVal.City) fmt.Printf("町域: %s\n", zipRes.AddressVal.Address) }
运行这段代码,你就能看到XML被成功解析成结构体实例,并且可以正常访问各个字段的值了。
内容的提问来源于stack exchange,提问作者kkkkgyg
相关产品推荐
相关产品推荐

