-
-
Notifications
You must be signed in to change notification settings - Fork 6.7k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
overload of at() with default value #133
Comments
I don't think this is a good idea, because I would like the |
OK, understood. |
Something equivalent of this would be great. I don't know why the STL doesn't have this. In C++17 there is insert_or_assign(), but no equivalent to python's dict.get() https://docs.python.org/2/library/stdtypes.html#dict.get. JsonCpp have this too http://open-source-parsers.github.io/jsoncpp-docs/doxygen/class_json_1_1_value.html#a28282c9b76fa031eba7a1843c47c16fe |
I'm on holiday right now. I'll have a look then. |
I think the Any name proposals better than |
Ah, insert_or_assign is different than want @dariomt is asking. I'm just suggesting to add insert_or_assign, it's added to the container types in c++17. I think at() is good name for what @dariomt wants and similar to the STL. Maybe at_default() is better? boost::property_tree might give some inspiration: http://www.boost.org/doc/libs/1_59_0/doc/html/property_tree/accessing.html |
maybe |
The standard containers' Qt's |
Good point with the reference! I guess |
What do you think of the following: value_type value(const typename object_t::key_type& key, value_type default_value = basic_json()) const
{
// at only works for objects
if (m_type != value_t::object)
{
throw std::domain_error("cannot use value() with " + type_name());
}
// if key is found, return value; otherwise, return given default value
auto it = find(key);
if (it != end())
{
return *it;
}
else
{
return default_value;
}
} It allows code like |
I forgot: Of course, the above could could be |
I like your proposed implementation. About returning the default value instead of throwing: from the perspective of least surprise I'd argue that Note that it's also easier to disallow other types first and to change the API later if users request it to work on other types as well then the other way around: if you allow it now and decide to disallow it later it would break the API and therefore potentially existing applications. |
As I mentioned in my original post, my use case is more in line with: template <typename T>
T value(const typename object_t::key_type& key, T default_value) const because when I'm looking for a key I already know the type the associated value should have, and I expect that I can get the converted-to-T value if the key is found, or the default-T if it is not found. To me that's the meaning |
I tried, but with the template I fail to compile a call like
When I write Any idea? |
My guess: My suggestion: add an overload to take care of that case, that creates a // overload for a default value of type const char*
StringType value(const typename object_t::key_type& key, const char* default_value) const
{
return value(key, StringType(default_value));
} If you don't like my suggestion, then you could |
If using the template, you need to make it deduce a type that is implicitly convertible both to and from value_type. This means that either you provide the T explicitly as in j.valuestd::string("key", "default string"), or you make sure that the default value is that type, as in j.value("key", "default string"s). To put the error at the point of use, you could add enable_if as you do in the constructors. |
I added the function with some documentation and example: http://nlohmann.github.io/json/classnlohmann_1_1basic__json_a26b7e4876af25eae5800ce43f93aaef2.html#a26b7e4876af25eae5800ce43f93aaef2 |
Hi there, one more question: What do you think of a second version of value_type value(const typename object_t::key_type &key) |
I think this "with default" version would be much more useful now that [] can no longer be used on const objects. I did a local build of our code with the updated version, and had to do a lot of replacing of foo[key] with *foo.find(key), and would much prefer foo.value(key). |
Ok, will so. |
Another idea for the version without explicit default value: Instead of returning |
After thinking about it for quite a while, removing the const version of |
My use case is:
e.g.
What do you think?
The text was updated successfully, but these errors were encountered: