impl/visit.hpp

100.0% Lines (66/66) 100.0% List of functions (3/3)
f(x) Functions (3)
Line TLA Hits Source Code
1 //
2 // Copyright (c) 2019 Vinnie Falco (vinnie.falco@gmail.com)
3 //
4 // Distributed under the Boost Software License, Version 1.0. (See accompanying
5 // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
6 //
7 // Official repository: https://github.com/boostorg/json
8 //
9
10 #ifndef BOOST_JSON_IMPL_VISIT_HPP
11 #define BOOST_JSON_IMPL_VISIT_HPP
12
13 namespace boost {
14 namespace json {
15
16 namespace detail {
17
18 extern
19 BOOST_JSON_DECL
20 std::nullptr_t stable_np;
21
22 } // namespace detail
23
24 template<class Visitor>
25 auto
26 16x visit(
27 Visitor&& v,
28 value& jv) -> decltype(
29 static_cast<Visitor&&>(v)( std::declval<std::nullptr_t&>() ) )
30 {
31 16x switch(jv.kind())
32 {
33 2x default: // unreachable()?
34 2x case kind::string: return static_cast<Visitor&&>(v)( jv.get_string() );
35 2x case kind::array: return static_cast<Visitor&&>(v)( jv.get_array() );
36 2x case kind::object: return static_cast<Visitor&&>(v)( jv.get_object() );
37 2x case kind::bool_: return static_cast<Visitor&&>(v)( jv.get_bool() );
38 2x case kind::int64: return static_cast<Visitor&&>(v)( jv.get_int64() );
39 2x case kind::uint64: return static_cast<Visitor&&>(v)( jv.get_uint64() );
40 2x case kind::double_: return static_cast<Visitor&&>(v)( jv.get_double() );
41 2x case kind::null: return static_cast<Visitor&&>(v)( detail::stable_np ) ;
42 }
43 }
44
45 template<class Visitor>
46 auto
47 264x visit(
48 Visitor&& v,
49 value const& jv) -> decltype(
50 static_cast<Visitor&&>(v)( std::declval<std::nullptr_t const&>() ) )
51 {
52 264x detail::scalar const& sc = detail::access::get_scalar(jv);
53 264x switch(jv.kind())
54 {
55 46x default: // unreachable()?
56 46x case kind::string: return static_cast<Visitor&&>(v)( jv.get_string() );
57 12x case kind::array: return static_cast<Visitor&&>(v)( jv.get_array() );
58 22x case kind::object: return static_cast<Visitor&&>(v)( jv.get_object() );
59 // local variables work around a bug in older clangs
60 30x case kind::bool_: {
61 30x bool const& b = sc.b;
62 30x return static_cast<Visitor&&>(v)(b);
63 }
64 92x case kind::int64: {
65 92x std::int64_t const& i = sc.i;
66 92x return static_cast<Visitor&&>(v)(i);
67 }
68 18x case kind::uint64: {
69 18x std::uint64_t const& u = sc.u;
70 18x return static_cast<Visitor&&>(v)(u);
71 }
72 10x case kind::double_: {
73 10x double const& d = sc.d;
74 10x return static_cast<Visitor&&>(v)(d);
75 }
76 34x case kind::null: {
77 34x auto const& np = detail::stable_np;
78 34x return static_cast<Visitor&&>(v)(np) ;
79 }
80 }
81 }
82
83
84 template<class Visitor>
85 auto
86 24x visit(
87 Visitor&& v,
88 value&& jv) -> decltype(
89 static_cast<Visitor&&>(v)( std::declval<std::nullptr_t&&>() ) )
90 {
91 24x switch(jv.kind())
92 {
93 3x default: // unreachable()?
94 3x case kind::string: return static_cast<Visitor&&>(v)(std::move( jv.get_string() ));
95 3x case kind::array: return static_cast<Visitor&&>(v)(std::move( jv.get_array() ));
96 3x case kind::object: return static_cast<Visitor&&>(v)(std::move( jv.get_object() ));
97 3x case kind::bool_: return static_cast<Visitor&&>(v)(std::move( detail::access::get_scalar(jv).b ));
98 3x case kind::int64: return static_cast<Visitor&&>(v)(std::move( detail::access::get_scalar(jv).i ));
99 3x case kind::uint64: return static_cast<Visitor&&>(v)(std::move( detail::access::get_scalar(jv).u ));
100 3x case kind::double_: return static_cast<Visitor&&>(v)(std::move( detail::access::get_scalar(jv).d ));
101 3x case kind::null: return static_cast<Visitor&&>(v)(std::move( detail::stable_np )) ;
102 }
103 }
104
105 } // namespace json
106 } // namespace boost
107
108 #endif
109