Reflection을 사용하여 JSON 역마샬링 사용자 정의
Go에서 JSON을 구조체로 역마샬링하는 것은 간단한 과정입니다. 그러나 json:"some_field"와 같은 사용자 정의 태그가 있는 필드를 처리할 때는 표준 역마샬링 메커니즘이 충분하지 않을 수 있습니다.
이 시나리오를 처리하는 한 가지 접근 방식은 리플렉션을 사용하는 것입니다. 리플렉션을 사용하여 구조체의 필드를 검사하면 필드에 특정 태그가 있는지 확인할 수 있고, 그렇다면 그에 따라 언마샬링을 처리할 수 있습니다.
이 특별한 경우에는 json 태그가 있는 필드가 다음과 같은지 확인하려고 합니다. 있는 그대로 문자열 필드로 비정렬화됩니다. 이를 통해 Go 구조체 내에서 JSON 객체 또는 배열을 처리할 수 있습니다.
예시 시나리오
다음 JSON 데이터와 Go 구조체를 고려하세요.
<code class="json">{ "I": 3, "S": { "phone": { "sales": "2223334444" } } }</code>
<code class="go">type A struct { I int64 S string `sql:"type:json"` }</code>
우리의 목표는 중첩된 JSON 구조를 유지하면서 "S" 필드를 문자열로 역마샬링하는 것입니다.
Reflection을 사용한 솔루션
다음 코드는 다음을 보여줍니다. 리플렉션을 사용하여 이를 달성하는 방법:
<code class="go">func main() { a := A{} // Unmarshal the JSON data into a byte slice var data []byte // Iterate over the fields of the struct typ := reflect.TypeOf(a) val := reflect.ValueOf(a) for i := 0; i < typ.NumField(); i++ { f := typ.Field(i) // Check if the field has a "json" tag if f.Tag.Get("json") == "" { continue } // Retrieve the field value fv := val.Field(i) // Unmarshall the JSON data into the field as a string if err := json.Unmarshal(data, &fv); err != nil { log.Fatal(err) } } fmt.Println(a) }</code>
이 접근 방식에서는 리플렉션을 사용하여 구조체의 각 필드를 수동으로 검사하여 "json" 태그가 있는지 확인합니다. 그렇다면 JSON 데이터를 문자열로 필드에 역마샬링합니다.
Custom Marshaler 및 Unmarshaler를 사용한 대체 솔루션
또 다른 옵션은 사용자 정의 유형을 구현하는 것입니다. json.Marshaler 및 json.Unmarshaler 인터페이스를 구현하는 RawString과 같은 것입니다. 이를 통해 역정렬화 프로세스를 더 유연하게 제어하고 제어할 수 있습니다.
이 접근 방식은 다음 코드에 나와 있습니다.
<code class="go">// RawString is a raw encoded JSON object. // It implements Marshaler and Unmarshaler and can // be used to delay JSON decoding or precompute a JSON encoding. type RawString string // MarshalJSON returns *m as the JSON encoding of m. func (m *RawString) MarshalJSON() ([]byte, error) { return []byte(*m), nil } // UnmarshalJSON sets *m to a copy of data. func (m *RawString) UnmarshalJSON(data []byte) error { if m == nil { return errors.New("RawString: UnmarshalJSON on nil pointer") } *m += RawString(data) return nil } const data = `{"i":3, "S":{"phone": {"sales": "2223334444"}}}` type A struct { I int64 S RawString `sql:"type:json"` } func main() { a := A{} err := json.Unmarshal([]byte(data), &a) if err != nil { log.Fatal("Unmarshal failed", err) } fmt.Println("Done", a) }</code>
자체 유형을 구현하면 역정렬화 프로세스를 사용자 정의하고 다음 코드를 피할 수 있습니다. 더 깨끗하고 효율적인 솔루션을 제공합니다.
위 내용은 Go에서 리플렉션을 사용하여 JSON 역마샬링을 사용자 정의하는 방법은 무엇입니까?의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!