c++ - 将 XPointer/XPath 搜索添加到所有(?) C++ JSON 库,是否可行?
问题描述
是否可以使用 XPath/XPointer 或仅使用一个 C++ 实现的子集来扩展所有(?)现有 C++ JSON 库?至少那些具有对象和数组值的迭代器?
我查看了三个 C++ JSON 库(查看 nlohmann、Boost.JSON 和 RapidJSON)来查看内部结构并检查它们的搜索功能。有些已经实现了Json 指针。Json 指针是基本的,几乎就像使用 json 作为名称-值列表一样。
XML 具有 XPath 和 XPointer 搜索,并且规则是标准化的。使用 XPath 和 XPointer,您可以做更多事情。
审查这些库的一个原因是看看是否可以用更好的搜索功能扩展它们。或者是否可以一次扩展所有(?)C++ JSON 库?
可以在此处找到描述此内容的较长文本,尽量简短。
我尝试使用一种遍历方法来选择具有一个特定属性名称的 json 值,并且该方法应该适用于所有经过测试的 JSON 库。如果我让它工作,可能会添加更多搜索逻辑并让它在几乎所有 C++ JSON 上工作。
我得到了这个 C++ 模板函数来处理所有经过测试的 json 库。它可以遍历 JSON 树并在所有测试的库上选择 json 值。
需要的是实现is_object
、is_array
、compare_name
、get_value
和begin
的专业化end
。那只是一个衬垫,所以很容易。
template<typename json_value>
bool is_object( const json_value* p )
{ static_assert(sizeof(json_value) == 0, "Only specializations of is_object is allowed"); }
template<typename json_value>
bool is_array( const json_value* p )
{ static_assert(sizeof(json_value) == 0, "Only specializations of is_array is allowed"); }
template<typename iterator>
bool compare_name( iterator it, std::string_view stringName )
{ static_assert(sizeof(it) == 0, "Only specializations of compare_name is allowed"); }
template<typename iterator, typename json_value>
const json_value* get_value( iterator it )
{ static_assert(sizeof(it) == 0, "Only specializations of get_value is allowed"); }
template<typename iterator, typename json_value>
iterator begin( const json_value& v ) { return std::begin( v ); }
template<typename iterator, typename json_value>
iterator end( const json_value& v ) { return std::end( v ); }
// ------------------------------------------------
// Selects all json values that match property name
template<typename json_value, typename object_iterator,typename array_iterator = object_iterator>
uint32_t select( const json_value& jsonValue, std::string_view stringQuery, std::vector<const json_value*>* pvectorValue = nullptr )
{ assert( is_object( &jsonValue ) || is_array( &jsonValue ) );
uint32_t uCount = 0;
if( is_object( &jsonValue ) == true ) // found object ?
{
for( auto it = begin<object_iterator,json_value>( jsonValue ); it != end<object_iterator,json_value>( jsonValue ); it++ )
{
if( is_object( get_value<object_iterator,json_value>( it ) ) == true )
{ // found object, scan it
auto value = get_value<object_iterator,json_value>( it );
uCount += select<json_value,object_iterator>( *value, stringQuery, pvectorValue );
}
else if( is_array( get_value<object_iterator,json_value>( it ) ) == true )
{ // found array, scan it
auto parray = get_value<object_iterator,json_value>( it );
uCount += select<json_value,object_iterator,array_iterator>( *parray, stringQuery, pvectorValue );
}
else if( compare_name<object_iterator>( it, stringQuery ) == true )
{ // property name matches, store value if pointer to vector
if( pvectorValue != nullptr ) pvectorValue->push_back( get_value<object_iterator,json_value>( it ) );
uCount++;
}
}
}
else if( is_array( &jsonValue ) == true ) // found array
{
for( auto it = begin<array_iterator,json_value>( jsonValue ); it != end<array_iterator,json_value>( jsonValue ); it++ )
{
if( is_object( get_value<array_iterator,json_value>( it ) ) == true )
{ // found object, scan it
auto value = get_value<array_iterator,json_value>( it );
uCount += select<json_value,object_iterator>( *value, stringQuery, pvectorValue );
}
else if( is_array( get_value<array_iterator,json_value>( it ) ) == true )
{ // found array, scan it
auto parray = get_value<array_iterator,json_value>( it );
uCount += select<json_value,object_iterator,array_iterator>( *parray, stringQuery, pvectorValue );
}
}
}
return uCount;
}
如果这可行并且如果我没有忘记某些东西,难道不应该只用一个实现来扩展所有库吗?XPath 和 XPointer 的附加逻辑不依赖于这些 C++ JSON 库的实现。
我错过了什么吗
解决方案
推荐阅读
- c - 在不关闭 MATLAB 的情况下停止 mex 函数 (C)
- python - 如何使用while循环修改Python中的列值
- angular - 当子组件在路由器出口Angular中时,从子组件调用父组件函数
- powershell - 如何从特定网站下载所有文件
- c# - 如何在 C# 中等待多个异步任务?
- java - com.mysql.jdbc.Driver 未加载。你确定你已经在 :jdbc_driver_library 中包含了正确的 jdbc 驱动程序吗?
- c# - 无法在文件中写入 AppedText
- regex - Ruby 看正则表达式错误:后看中的无效模式
- php - PHP 垃圾收集似乎没有运行 (Debian)
- formatting - 如何创建引导线以将标签连接到符号系统