2017-02-15 94 views
4

目前我正在编写一个C++应用程序,我必须连接到SQLite数据库。我寻找一个图书馆,找到了SOCI,我不得不说:我喜欢它。流语法和映射非常棒。但我有一个问题吧:C++ SOCI查询到自定义对象的向量

我有一个事件等级和我写的分析器功能吧:

template<> struct type_conversion<Event> 
{ 
    typedef values base_type; 

    static void from_base(const values& v, indicator /* ind */, Event& event) 
    { 
     event.m_id = v.get<std::string>("id"); 
     event.m_title = v.get<std::string>("Title"); 
     event.m_description = v.get<std::string>("Description"); 
     event.m_date = v.get<std::tm>("Date"); 
    } 

    static void to_base(const Event& event, values& v, indicator& ind) 
    { 
     v.set("id", event.m_id); 
     v.set("Title", event.m_title); 
     v.set("Description", event.m_description); 
     v.set("Date", event.m_date); 

     ind = i_ok; 
    } 
}; 

这像这样的查询的伟大工程:

sql << "SELECT * FROM Event WHERE id=5", into(event); 

我想选择一大堆活动到std::vector<Event*>,但如果我试着这个:

std::vector<Event*> events; 
sql << "SELECT * FROM Event", into(events) 

但与此我得到以下编译器错误:

No known convertation from 
soci::details::conversion_into_type<std::vector<Event>> into 
soci::details::into_type_base 

是不是可能与SOCI或我错过了什么?我也发现OTL作为图书馆。这可能是一个很好的选择?正如我所说我喜欢SOCI的方式。 OTL也可以这样做吗?

回答

4

SOCI不支持ORM与批量操作的组合。查看邮件列表线程:ORM with std::vector not supported?

相反,你可以使用基于迭代器行集和访问:

rowset<Event> rs = (sql.prepare << "SELECT * FROM Event"); 
for (auto it = rs.cbegin(); it != rs.cend(); ++it) 
{ 
    // access event 
} 

AFAIR,它仍然应该得到支持。

+0

非常感谢你!我还有两个问题:如果我再次执行相同的查询,SOCI会在后台缓存对象吗?那么将'rowset'声明为朋友的正确方法是什么,这样我可以使默认构造函数是私有的?我试过'朋友类soci :: rowset '但这不起作用。 – Cilenco

+0

SOCI在发出单独查询之间不会缓存任何内容。用于专门化行集的类型必须是默认可构造的。 – mloskot

+0

如果rowset是我的类的一个朋友,并且构造函数是私人的,或者我误解了你,它应该是默认构造的? – Cilenco