11#include " simdjson.h"
2+ #include " simdjson/json_builder/json_builder.h"
23#include < string>
34#include < vector>
45#include < iostream>
56#include < type_traits>
67
78using namespace simdjson ;
89
10+ // Example user-defined type
11+ struct MyStruct {
12+ int id;
13+ std::string name;
14+ std::vector<int > values;
15+ };
16+
17+ // Example of simple user-defined type
18+ struct MySimpleStruct {
19+ int id;
20+ std::string name;
21+ };
22+
923namespace simdjson {
1024
1125template <typename T>
@@ -16,7 +30,7 @@ concept PushableContainer =
1630 !std::is_same_v<T, std::string_view> &&
1731 !std::is_same_v<T, const char *>;
1832
19- // Specialize tag_invoke for std::vector<int>
33+ // Specialize tag_invoke for containers
2034template <typename T>
2135 requires PushableContainer<T>
2236simdjson_result<T>
@@ -52,11 +66,49 @@ tag_invoke(deserialize_tag, std::type_identity<T>, ondemand::value &val) {
5266 }
5367
5468 return vec;
69+ }
70+
71+ template <typename T>
72+ requires json_builder::UserDefinedType<T>
73+ simdjson_result<T>
74+ tag_invoke (deserialize_tag, std::type_identity<T>, ondemand::value &val) {
75+ ondemand::object obj;
76+ auto error = val.get_object ().get (obj);
77+ if (error) {
78+ return error;
79+ }
80+ T t;
81+ [:json_builder::expand (std::meta::nonstatic_data_members_of (^T)):] >> [&]<auto mem> {
82+ auto it = obj[to_string_view (std::meta::identifier_of (mem))];
83+ using MemberType = typename std::remove_reference_t <decltype (t.[:mem:])>;
84+
85+ if constexpr (std::is_same_v<MemberType, int >) {
86+ auto int_result = it.get_int64 ();
87+ if (int_result.error ()) throw std::runtime_error (" Error getting int64" );
88+ t.[:mem:] = static_cast <int >(int_result.value ());
89+ } else if constexpr (std::is_same_v<MemberType, double >) {
90+ auto double_result = it.get_double ();
91+ if (double_result.error ()) throw std::runtime_error (" Error getting double" );
92+ t.[:mem:] = double_result.value ();
93+ } else if constexpr (std::is_same_v<MemberType, std::string>) {
94+ auto string_result = it.get_string ();
95+ if (string_result.error ()) throw std::runtime_error (" Error getting string" );
96+ t.[:mem:] = std::string (string_result.value ());
97+ } else if constexpr (std::is_same_v<MemberType, bool >) {
98+ auto bool_result = it.get_bool ();
99+ if (bool_result.error ()) throw std::runtime_error (" Error getting bool" );
100+ t.[:mem:] = bool_result.value ();
101+ } else {
102+ t.[:mem:] = it.template get <MemberType>().value ();
103+ }
104+ };
105+ return t;
55106}
56107
57- } // namespace simdjson
108+ } // simdjson
58109
59110int main () {
111+ // Test for std::vector<int>
60112 std::string json_str = R"( {"values": [1, 2, 3]})" ;
61113 ondemand::parser parser;
62114 auto doc = parser.iterate(json_str);
@@ -67,10 +119,27 @@ int main() {
67119 return 1 ;
68120 }
69121
70- std::vector<int > my_struct = result.value ();
71- for (const int &x : my_struct ) {
122+ std::vector<int > z = result.value ();
123+ for (const int &x : z ) {
72124 std::cout << x << std::endl;
73125 }
74126
127+ // Test for user-defined type MyStruct
128+ std::string json_str3 = R"( {"id": 1, "name": "example", "values": [1, 2, 3]})" ;
129+ ondemand::parser parser3;
130+ auto doc3 = parser3.iterate(json_str3);
131+
132+ auto result3 = doc3.get <MyStruct>();
133+ if (result3.error ()) {
134+ std::cerr << " Error parsing JSON: " << result3.error () << std::endl;
135+ return 1 ;
136+ }
137+
138+ MyStruct my_struct = result3.value ();
139+ std::cout << " ID: " << my_struct.id << " , Name: " << my_struct.name << " , Values: " ;
140+ for (const int &x : my_struct.values ) {
141+ std::cout << x << " " ;
142+ }
143+ std::cout << std::endl;
75144 return 0 ;
76145}
0 commit comments